Squash: Fix bugs
|
@ -1,9 +1,9 @@
|
|||
---
|
||||
name: File bug
|
||||
about: File bug to improve SRS
|
||||
name: Bug report
|
||||
about: Create a report to help us improve
|
||||
title: ''
|
||||
labels: ''
|
||||
assignees: 'winlinvip'
|
||||
assignees: ''
|
||||
|
||||
---
|
||||
|
||||
|
@ -16,17 +16,15 @@ assignees: 'winlinvip'
|
|||
1. SRS版本(Version): `xxxxxx`
|
||||
|
||||
1. SRS的日志如下(Log):
|
||||
|
||||
```
|
||||
|
||||
xxxxxxxxxxxx
|
||||
|
||||
```
|
||||
|
||||
1. SRS的配置如下(Config):
|
||||
|
||||
```
|
||||
|
||||
xxxxxxxxxxxx
|
||||
|
||||
```
|
||||
|
||||
**重现(Replay)**
|
20
.github/ISSUE_TEMPLATE/feature_request.md
vendored
Normal file
|
@ -0,0 +1,20 @@
|
|||
---
|
||||
name: Feature request
|
||||
about: Suggest an idea for this project
|
||||
title: ''
|
||||
labels: ''
|
||||
assignees: ''
|
||||
|
||||
---
|
||||
|
||||
**Is your feature request related to a problem? Please describe.**
|
||||
A clear and concise description of what the problem is. Ex. I'm always frustrated when [...]
|
||||
|
||||
**Describe the solution you'd like**
|
||||
A clear and concise description of what you want to happen.
|
||||
|
||||
**Describe alternatives you've considered**
|
||||
A clear and concise description of any alternative solutions or features you've considered.
|
||||
|
||||
**Additional context**
|
||||
Add any other context or screenshots about the feature request here.
|
7
.github/pull_request_template.md
vendored
Normal file
|
@ -0,0 +1,7 @@
|
|||
## Summary
|
||||
|
||||
Please describe the summary for this PR.
|
||||
|
||||
## Details
|
||||
|
||||
Add more details about this PR.
|
2
.github/workflows/release.yml
vendored
|
@ -137,7 +137,7 @@ jobs:
|
|||
* Source: ${{ env.SRS_SOURCE_MD5 }} [${{ env.SRS_SOURCE_TAR }}](https://github.com/ossrs/srs/releases/download/${{ env.SRS_TAG }}/${{ env.SRS_SOURCE_TAR }})
|
||||
* Binary: ${{ env.SRS_PACKAGE_MD5 }} [${{ env.SRS_PACKAGE_ZIP }}](https://github.com/ossrs/srs/releases/download/${{ env.SRS_TAG }}/${{ env.SRS_PACKAGE_ZIP }})
|
||||
draft: false
|
||||
prerelease: true
|
||||
prerelease: false
|
||||
# Upload release source files
|
||||
- name: Upload Release Assets Source
|
||||
id: upload-release-assets-source
|
||||
|
|
128
CODE_OF_CONDUCT.md
Normal file
|
@ -0,0 +1,128 @@
|
|||
# Contributor Covenant Code of Conduct
|
||||
|
||||
## Our Pledge
|
||||
|
||||
We as members, contributors, and leaders pledge to make participation in our
|
||||
community a harassment-free experience for everyone, regardless of age, body
|
||||
size, visible or invisible disability, ethnicity, sex characteristics, gender
|
||||
identity and expression, level of experience, education, socio-economic status,
|
||||
nationality, personal appearance, race, religion, or sexual identity
|
||||
and orientation.
|
||||
|
||||
We pledge to act and interact in ways that contribute to an open, welcoming,
|
||||
diverse, inclusive, and healthy community.
|
||||
|
||||
## Our Standards
|
||||
|
||||
Examples of behavior that contributes to a positive environment for our
|
||||
community include:
|
||||
|
||||
* Demonstrating empathy and kindness toward other people
|
||||
* Being respectful of differing opinions, viewpoints, and experiences
|
||||
* Giving and gracefully accepting constructive feedback
|
||||
* Accepting responsibility and apologizing to those affected by our mistakes,
|
||||
and learning from the experience
|
||||
* Focusing on what is best not just for us as individuals, but for the
|
||||
overall community
|
||||
|
||||
Examples of unacceptable behavior include:
|
||||
|
||||
* The use of sexualized language or imagery, and sexual attention or
|
||||
advances of any kind
|
||||
* Trolling, insulting or derogatory comments, and personal or political attacks
|
||||
* Public or private harassment
|
||||
* Publishing others' private information, such as a physical or email
|
||||
address, without their explicit permission
|
||||
* Other conduct which could reasonably be considered inappropriate in a
|
||||
professional setting
|
||||
|
||||
## Enforcement Responsibilities
|
||||
|
||||
Community leaders are responsible for clarifying and enforcing our standards of
|
||||
acceptable behavior and will take appropriate and fair corrective action in
|
||||
response to any behavior that they deem inappropriate, threatening, offensive,
|
||||
or harmful.
|
||||
|
||||
Community leaders have the right and responsibility to remove, edit, or reject
|
||||
comments, commits, code, wiki edits, issues, and other contributions that are
|
||||
not aligned to this Code of Conduct, and will communicate reasons for moderation
|
||||
decisions when appropriate.
|
||||
|
||||
## Scope
|
||||
|
||||
This Code of Conduct applies within all community spaces, and also applies when
|
||||
an individual is officially representing the community in public spaces.
|
||||
Examples of representing our community include using an official e-mail address,
|
||||
posting via an official social media account, or acting as an appointed
|
||||
representative at an online or offline event.
|
||||
|
||||
## Enforcement
|
||||
|
||||
Instances of abusive, harassing, or otherwise unacceptable behavior may be
|
||||
reported to the community leaders responsible for enforcement at
|
||||
winlin@vip.126.com.
|
||||
All complaints will be reviewed and investigated promptly and fairly.
|
||||
|
||||
All community leaders are obligated to respect the privacy and security of the
|
||||
reporter of any incident.
|
||||
|
||||
## Enforcement Guidelines
|
||||
|
||||
Community leaders will follow these Community Impact Guidelines in determining
|
||||
the consequences for any action they deem in violation of this Code of Conduct:
|
||||
|
||||
### 1. Correction
|
||||
|
||||
**Community Impact**: Use of inappropriate language or other behavior deemed
|
||||
unprofessional or unwelcome in the community.
|
||||
|
||||
**Consequence**: A private, written warning from community leaders, providing
|
||||
clarity around the nature of the violation and an explanation of why the
|
||||
behavior was inappropriate. A public apology may be requested.
|
||||
|
||||
### 2. Warning
|
||||
|
||||
**Community Impact**: A violation through a single incident or series
|
||||
of actions.
|
||||
|
||||
**Consequence**: A warning with consequences for continued behavior. No
|
||||
interaction with the people involved, including unsolicited interaction with
|
||||
those enforcing the Code of Conduct, for a specified period of time. This
|
||||
includes avoiding interactions in community spaces as well as external channels
|
||||
like social media. Violating these terms may lead to a temporary or
|
||||
permanent ban.
|
||||
|
||||
### 3. Temporary Ban
|
||||
|
||||
**Community Impact**: A serious violation of community standards, including
|
||||
sustained inappropriate behavior.
|
||||
|
||||
**Consequence**: A temporary ban from any sort of interaction or public
|
||||
communication with the community for a specified period of time. No public or
|
||||
private interaction with the people involved, including unsolicited interaction
|
||||
with those enforcing the Code of Conduct, is allowed during this period.
|
||||
Violating these terms may lead to a permanent ban.
|
||||
|
||||
### 4. Permanent Ban
|
||||
|
||||
**Community Impact**: Demonstrating a pattern of violation of community
|
||||
standards, including sustained inappropriate behavior, harassment of an
|
||||
individual, or aggression toward or disparagement of classes of individuals.
|
||||
|
||||
**Consequence**: A permanent ban from any sort of public interaction within
|
||||
the community.
|
||||
|
||||
## Attribution
|
||||
|
||||
This Code of Conduct is adapted from the [Contributor Covenant][homepage],
|
||||
version 2.0, available at
|
||||
https://www.contributor-covenant.org/version/2/0/code_of_conduct.html.
|
||||
|
||||
Community Impact Guidelines were inspired by [Mozilla's code of conduct
|
||||
enforcement ladder](https://github.com/mozilla/diversity).
|
||||
|
||||
[homepage]: https://www.contributor-covenant.org
|
||||
|
||||
For answers to common questions about this code of conduct, see the FAQ at
|
||||
https://www.contributor-covenant.org/faq. Translations are available at
|
||||
https://www.contributor-covenant.org/translations.
|
5
CONTRIBUTING.md
Normal file
|
@ -0,0 +1,5 @@
|
|||
Welome to contribute to SRS!
|
||||
|
||||
1. Please read [FAQ](https://github.com/ossrs/srs/issues/2716) before file new PR.
|
||||
2. Fix some [issues](https://github.com/ossrs/srs/issues), then follow the [guide](https://github.com/ossrs/srs/wiki/HowToFilePR).
|
||||
3. We will review your PR ASAP.
|
|
@ -15,7 +15,7 @@
|
|||
[![](https://img.shields.io/twitch/status/winlinvip?style=social)](https://www.twitch.tv/winlinvip)
|
||||
[![](https://badgen.net/discord/members/yZ4BnPmHAd)](https://discord.gg/yZ4BnPmHAd)
|
||||
[![](https://opencollective.com/srs-server/tiers/badge.svg)](https://opencollective.com/srs-server/contribute)
|
||||
[![](https://badgen.net/badge/stackoverflow/srs/green?icon=wiki)](https://stackoverflow.com/questions/tagged/simple-realtime-server)
|
||||
[![](https://stackoverflow-badge.herokuapp.com/api/StackOverflowBadge/17679565)](https://stackoverflow.com/questions/tagged/simple-realtime-server)
|
||||
|
||||
SRS/5.0,[Bee](https://github.com/ossrs/srs/wiki/Product#release50) 是一个简单高效的实时视频服务器,支持RTMP/WebRTC/HLS/HTTP-FLV/SRT。
|
||||
|
||||
|
@ -111,6 +111,7 @@ A big `THANK YOU` also goes to:
|
|||
|
||||
## Releases
|
||||
|
||||
* 2021-12-19, Release [v4.0-b1](https://github.com/ossrs/srs/releases/tag/v4.0-b1), v4.0-b1, 4.0 beta1, v4.0.206, 144126 lines.
|
||||
* 2021-12-01, Release [v4.0-b0](https://github.com/ossrs/srs/releases/tag/v4.0-b0), v4.0-b0, 4.0 beta0, v4.0.201, 144022 lines.
|
||||
* 2021-11-15, Release [v4.0.198](https://github.com/ossrs/srs/releases/tag/v4.0.198), 4.0 dev8, v4.0.198, 144010 lines.
|
||||
* 2021-11-02, Release [v4.0.191](https://github.com/ossrs/srs/releases/tag/v4.0.191), 4.0 dev7, v4.0.191, 143890 lines.
|
||||
|
|
6
trunk/3rdparty/README.md
vendored
|
@ -41,10 +41,10 @@ opus-1.3.1.tar.gz
|
|||
gtest-1.6.0.zip
|
||||
* google test framework.
|
||||
* https://code.google.com/p/googletest/downloads/list
|
||||
|
||||
gperftools-2.1.zip
|
||||
|
||||
gperftools-2-fit
|
||||
* gperf tools for performance benchmark.
|
||||
* https://code.google.com/p/gperftools/downloads/list
|
||||
* https://github.com/gperftools/gperftools/releases/tag/gperftools-2.9.1
|
||||
|
||||
st-srs
|
||||
st-1.9.zip
|
||||
|
|
2
trunk/3rdparty/gperftools-2-fit/AUTHORS
vendored
Normal file
|
@ -0,0 +1,2 @@
|
|||
google-perftools@googlegroups.com
|
||||
|
28
trunk/3rdparty/gperftools-2-fit/COPYING
vendored
Normal file
|
@ -0,0 +1,28 @@
|
|||
Copyright (c) 2005, Google Inc.
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions are
|
||||
met:
|
||||
|
||||
* Redistributions of source code must retain the above copyright
|
||||
notice, this list of conditions and the following disclaimer.
|
||||
* Redistributions in binary form must reproduce the above
|
||||
copyright notice, this list of conditions and the following disclaimer
|
||||
in the documentation and/or other materials provided with the
|
||||
distribution.
|
||||
* Neither the name of Google Inc. nor the names of its
|
||||
contributors may be used to endorse or promote products derived from
|
||||
this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
||||
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||||
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
||||
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
|
||||
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
||||
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
14434
trunk/3rdparty/gperftools-2-fit/ChangeLog
vendored
Normal file
646
trunk/3rdparty/gperftools-2-fit/ChangeLog.old
vendored
Normal file
|
@ -0,0 +1,646 @@
|
|||
Fri Feb 03 15:40:45 2012 Google Inc. <google-perftools@googlegroups.com>
|
||||
|
||||
* gperftools: version 2.0
|
||||
* Renamed the project from google-perftools to gperftools (csilvers)
|
||||
* Renamed the .deb/.rpm packagse from google-perftools to gperftools too
|
||||
* Renamed include directory from google/ to gperftools/ (csilvers)
|
||||
* Changed the 'official' perftools email in setup.py/etc
|
||||
* Renamed google-perftools.sln to gperftools.sln
|
||||
* PORTING: Removed bash-isms & grep -q in heap-checker-death_unittest.sh
|
||||
* Changed copyright text to reflect Google's relinquished ownership
|
||||
|
||||
Tue Jan 31 10:43:50 2012 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 1.10 release
|
||||
* PORTING: Support for patching assembly on win x86_64! (scott.fr...)
|
||||
* PORTING: Work around atexit-execution-order bug on freebsd (csilvers)
|
||||
* PORTING: Patch _calloc_crt for windows (roger orr)
|
||||
* PORTING: Add C++11 compatibility method for stl allocator (jdennett)
|
||||
* PORTING: use MADV_FREE, not MADV_DONTNEED, on freebsd (csilvers)
|
||||
* PORTING: Don't use SYS_open when not supported on solaris (csilvers)
|
||||
* PORTING: Do not assume uname() returns 0 on success (csilvers)
|
||||
* LSS: Improved ARM support in linux-syscall-support (dougkwan)
|
||||
* LSS: Get rid of unused syscalls in linux-syscall-support (csilvers)
|
||||
* LSS: Fix broken mmap wrapping for ppc (markus)
|
||||
* LSS: Emit .cfi_adjust_cfa_offset when appropriate (ppluzhnikov)
|
||||
* LSS: Be more accurate in register use in __asm__ (markus)
|
||||
* LSS: Fix __asm__ calls to compile under clang (chandlerc)
|
||||
* LSS: Fix ARM inline assembly bug around r7 and swi (lcwu)
|
||||
* No longer log when an allocator fails (csilvers)
|
||||
* void* -> const void* for MallocExtension methods (llib)
|
||||
* Improve HEAP_PROFILE_MMAP and fix bugs with it (dmikurube)
|
||||
* Replace int-based abs with more correct fabs in a test (pmurin)
|
||||
|
||||
Thu Dec 22 16:22:45 2011 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 1.9 release
|
||||
* Lightweight check for double-frees (blount)
|
||||
* BUGFIX: Fix pprof to exit properly if run with no args (dagitses)
|
||||
* Suggest ASan as a way to diagnose buggy code (ppluzhnikov)
|
||||
* Get rid of unused CACHELINE_SIZE (csilvers)
|
||||
* Replace atexit() calls with global dtors; helps freebsd (csilvers)
|
||||
* Disable heap-checker under AddressSanitizer (kcc)
|
||||
* Fix bug in powerpc stacktracing (ppluzhnikov)
|
||||
* PERF: Use exponential backoff waiting for spinlocks (m3b)
|
||||
* Fix 64-bit nm on 32-bit binaries in pprof (csilvers)
|
||||
* Add ProfileHandlerDisallowForever (rsc)
|
||||
* BUGFIX: Shell escape when forking in pprof (csilvers)
|
||||
* No longer combine overloaded functions in pprof (csilvers)
|
||||
* Fix address-normalizing bug in pprof (csilvers)
|
||||
* More consistently call abort() instead of exit() on failure (csilvers)
|
||||
* Allow NoGlobalLeaks to be safely called more than once (csilvers)
|
||||
* PORTING/BUGFIX: Fix ARM cycleclock to use volatile asm (dougkwan)
|
||||
* PORTING: 64-bit atomic ops for ARMv7 (dougkwan)
|
||||
* PORTING: Implement stacktrace for ARM (dougkwan)
|
||||
* PORTING: Fix malloc_hook_mmap_linux for ARM (dougkwan)
|
||||
* PORTING: Update linux_syscall_support.h for ARM/etc (evannier, sanek)
|
||||
* PORTING: Fix freebsd to work on x86_64 (chapp...@gmail.com)
|
||||
* PORTING: Added additional SYS_mmap fixes for FreeBSD (chappedm)
|
||||
* PORTING: Allow us to compile on OS X 10.6 and run on 10.5 (raltherr)
|
||||
* PORTING: Check for mingw compilers that *do* define timespec
|
||||
* PORTING: Add "support" for MIPS cycletimer
|
||||
* PORTING: Fix fallback cycle-timer to work with Now (dougkwan)
|
||||
* PERF: Move stack trace collecting out of the mutex (taylorc)
|
||||
* PERF: Get the deallocation stack trace outside the mutex (sean)
|
||||
* Make PageHeap dynamically allocated for leak checks (maxim)
|
||||
* BUGFIX: Fix probing of nm -f behavior in pprof (dpeng)
|
||||
* BUGFIX: Fix a race with the CentralFreeList lock before main (sanjay)
|
||||
* Support /pprof/censusprofile url arguments (rajatjain)
|
||||
* Change IgnoreObject to return its argument (nlewycky)
|
||||
* Update malloc-hook files to support more CPUs
|
||||
* BUGFIX: write our own strstr to avoid libc problems (csilvers)
|
||||
* Use simple callgrind compression facility in pprof
|
||||
* Print an error message when we can't run pprof to symbolize (csilvers)
|
||||
* Die in configure when g++ is't installed (csilvers)
|
||||
* DOC: Beef up the documentation a bit about using libunwind (csilvers)
|
||||
|
||||
Fri Aug 26 13:29:25 2011 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 1.8.3 release
|
||||
* Added back the 'pthreads unsafe early' #define, needed for FreeBSD
|
||||
|
||||
Thu Aug 11 15:01:47 2011 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 1.8.2 release
|
||||
* Fixed calculation of patchlevel, 'make check' should all pass again
|
||||
|
||||
Tue Jul 26 20:57:51 2011 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 1.8.1 release
|
||||
* Added an #include to fix compile breakage on latest gcc's
|
||||
* Removed an extra , in the configure.ac script
|
||||
|
||||
Fri Jul 15 16:10:51 2011 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 1.8 release
|
||||
* PORTING: (Disabled) support for patching mmap on freebsd (chapp...)
|
||||
* PORTING: Support volatile __malloc_hook for glibc 2.14 (csilvers)
|
||||
* PORTING: Use _asm rdtsc and __rdtsc to get cycleclock in windows (koda)
|
||||
* PORTING: Fix fd vs. HANDLE compiler error on cygwin (csilvers)
|
||||
* PORTING: Do not test memalign or double-linking on OS X (csilvers)
|
||||
* PORTING: Actually enable TLS on windows (jontra)
|
||||
* PORTING: Some work to compile under Native Client (krasin)
|
||||
* PORTING: deal with pthread_once w/o -pthread on freebsd (csilvers)
|
||||
* Rearrange libc-overriding to make it easier to port (csilvers)
|
||||
* Display source locations in pprof disassembly (sanjay)
|
||||
* BUGFIX: Actually initialize allocator name (mec)
|
||||
* BUGFIX: Keep track of 'overhead' bytes in malloc reporting (csilvers)
|
||||
* Allow ignoring one object twice in the leak checker (glider)
|
||||
* BUGFIX: top10 in pprof should print 10 lines, not 11 (rsc)
|
||||
* Refactor vdso source files (tipp)
|
||||
* Some documentation cleanups
|
||||
* Document MAX_TOTAL_THREAD_CACHE_SIZE <= 1Gb (nsethi)
|
||||
* Add MallocExtension::GetOwnership(ptr) (csilvers)
|
||||
* BUGFIX: We were leaving out a needed $(top_srcdir) in the Makefile
|
||||
* PORTING: Support getting argv0 on OS X
|
||||
* Add 'weblist' command to pprof: like 'list' but html (sanjay)
|
||||
* Improve source listing in pprof (sanjay)
|
||||
* Cap cache sizes to reduce fragmentation (ruemmler)
|
||||
* Improve performance by capping or increasing sizes (ruemmler)
|
||||
* Add M{,un}mapReplacmenet hooks into MallocHook (ribrdb)
|
||||
* Refactored system allocator logic (gangren)
|
||||
* Include cleanups (csilvers)
|
||||
* Add TCMALLOC_SMALL_BUT_SLOW support (ruemmler)
|
||||
* Clarify that tcmalloc stats are MiB (robinson)
|
||||
* Remove support for non-tcmalloc debugallocation (blount)
|
||||
* Add a new test: malloc_hook_test (csilvers)
|
||||
* Change the configure script to be more crosstool-friendly (mcgrathr)
|
||||
* PORTING: leading-underscore changes to support win64 (csilvers)
|
||||
* Improve debugallocation tc_malloc_size (csilvers)
|
||||
* Extend atomicops.h and cyceclock to use ARM V6+ optimized code (sanek)
|
||||
* Change malloc-hook to use a list-like structure (llib)
|
||||
* Add flag to use MAP_PRIVATE in memfs_malloc (gangren)
|
||||
* Windows support for pprof: nul and /usr/bin/file (csilvers)
|
||||
* TESTING: add test on strdup to tcmalloc_test (csilvers)
|
||||
* Augment heap-checker to deal with no-inode maps (csilvers)
|
||||
* Count .dll/.dylib as shared libs in heap-checker (csilvers)
|
||||
* Disable sys_futex for arm; it's not always reliable (sanek)
|
||||
* PORTING: change lots of windows/port.h macros to functions
|
||||
* BUGFIX: Generate correct version# in tcmalloc.h on windows (csilvers)
|
||||
* PORTING: Some casting to make solaris happier about types (csilvers)
|
||||
* TESTING: Disable debugallocation_test in 'minimal' mode (csilvers)
|
||||
* Rewrite debugallocation to be more modular (csilvers)
|
||||
* Don't try to run the heap-checker under valgrind (ppluzhnikov)
|
||||
* BUGFIX: Make focused stat %'s relative, not absolute (sanjay)
|
||||
* BUGFIX: Don't use '//' comments in a C file (csilvers)
|
||||
* Quiet new-gcc compiler warnings via -Wno-unused-result, etc (csilvers)
|
||||
|
||||
Fri Feb 04 15:54:31 2011 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 1.7 release
|
||||
* Reduce page map key size under x86_64 by 4.4MB (rus)
|
||||
* Remove a flaky malloc-extension test (fdabek)
|
||||
* Improve the performance of PageHeap::New (ond..., csilvers)
|
||||
* Improve sampling_test with no-inline additions/etc (fdabek)
|
||||
* 16-byte align debug allocs (jyasskin)
|
||||
* Change FillProcSelfMaps to detect out-of-buffer-space (csilvers)
|
||||
* Document the need for sampling to use GetHeapSample (csilvers)
|
||||
* Try to read TSC frequency from tsc_freq_khs (adurbin)
|
||||
* Do better at figuring out if tests are running under gdb (ppluzhnikov)
|
||||
* Improve spinlock contention performance (ruemmler)
|
||||
* Better internal-function list for pprof's /contention (ruemmler)
|
||||
* Speed up GoogleOnce (m3b)
|
||||
* Limit number of incoming/outgoing edges in pprof (sanjay)
|
||||
* Add pprof --evince to go along with --gv (csilvers)
|
||||
* Document the various ways to get heap-profiling information (csilvers)
|
||||
* Separate out synchronization profiling routines (ruemmler)
|
||||
* Improve malloc-stats output to be more understandable (csilvers)
|
||||
* Add support for census profiler in pporf (nabeelmian)
|
||||
* Document how pprof's /symbol must support GET requests (csilvers)
|
||||
* Improve acx_pthread.m4 (ssuomi, liujisi)
|
||||
* Speed up pprof's ExtractSymbols (csilvers)
|
||||
* Ignore some known-leaky (java) libraries in the heap checker (davidyu)
|
||||
* Make kHideMask use all 64 bits in tests (ppluzhnikov)
|
||||
* Clean up pprof input-file handling (csilvers)
|
||||
* BUGFIX: Don't crash if __environ is NULL (csilvers)
|
||||
* BUGFIX: Fix totally broken debugallocation tests (csilvers)
|
||||
* BUGFIX: Fix up fake_VDSO handling for unittest (ppluzhnikov)
|
||||
* BUGFIX: Suppress all large allocs when report threshold is 0 (lexie)
|
||||
* BUGFIX: mmap2 on i386 takes an off_t, not off64_t (csilvers)
|
||||
* PORTING: Add missing PERFTOOLS_DLL_DECL (csilvers)
|
||||
* PORTING: Add stddef.h to make newer gcc's happy (csilvers)
|
||||
* PORTING: Document some tricks for working under OS X (csilvers)
|
||||
* PORTING: Don't try to check valgrind for windows (csilvers)
|
||||
* PORTING: Make array-size a var to compile under clang (chandlerc)
|
||||
* PORTING: No longer hook _aligned_malloc and _aligned_free (csilvers)
|
||||
* PORTING: Quiet some gcc warnings (csilvers)
|
||||
* PORTING: Replace %PRIxPTR with %p to be more portable (csilvers)
|
||||
* PORTING: Support systems that capitalize /proc weirdly (sanek)
|
||||
* PORTING: Treat arm3 the same as arm5t in cycletimer (csilvers)
|
||||
* PORTING: Update windows logging to not allocate memory (csilvers)
|
||||
* PORTING: avoid double-patching newer windows DLLs (roger.orr)
|
||||
* PORTING: get dynamic_annotations.c to work on windows (csilvers)
|
||||
* Add pkg-config .pc files for the 5 libraries we produce (csilvers)
|
||||
* Added proper libtool versioning, so this lib will be 0.1.0 (csilvers)
|
||||
* Moved from autoconf 2.64 to 2.65
|
||||
|
||||
Thu Aug 5 12:48:03 PDT 2010 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 1.6 release
|
||||
* Add tc_malloc_usable_size for compatibility with glibc (csilvers)
|
||||
* Override malloc_usable_size with tc_malloc_usable_size (csilvers)
|
||||
* Default to no automatic heap sampling in tcmalloc (csilvers)
|
||||
* Add -DTCMALLOC_LARGE_PAGES, a possibly faster tcmalloc (rus)
|
||||
* Make some functions extern "C" to avoid false ODR warnings (jyasskin)
|
||||
* pprof: Add SVG-based output (rsc)
|
||||
* pprof: Extend pprof --tools to allow per-tool configs (csilvers)
|
||||
* pprof: Improve support of 64-bit and big-endian profiles (csilvers)
|
||||
* pprof: Add interactive callgrind suport (weidenri...)
|
||||
* pprof: Improve address->function mapping a bit (dpeng)
|
||||
* Better detection of when we're running under valgrind (csilvers)
|
||||
* Better CPU-speed detection under valgrind (saito)
|
||||
* Use, and recommend, -fno-builtin-malloc when compiling (csilvers)
|
||||
* Avoid false-sharing of memory between caches (bmaurer)
|
||||
* BUGFIX: Fix heap sampling to use correct alloc size (bmauer)
|
||||
* BUGFIX: Avoid gcc 4.0.x bug by making hook-clearing atomic (csilvers)
|
||||
* BUGFIX: Avoid gcc 4.5.x optimization bug (csilvers)
|
||||
* BUGFIX: Work around deps-determining bug in libtool 1.5.26 (csilvers)
|
||||
* BUGFIX: Fixed test to use HAVE_PTHREAD, not HAVE_PTHREADS (csilvers)
|
||||
* BUGFIX: Fix tls callback behavior on windows when using wpo (wtc)
|
||||
* BUGFIX: properly align allocation sizes on Windows (antonm)
|
||||
* BUGFIX: Fix prototypes for tcmalloc/debugalloc wrt throw() (csilvers)
|
||||
* DOC: Updated heap-checker doc to match reality better (fischman)
|
||||
* DOC: Document ProfilerFlush, ProfilerStartWithOptions (csilvers)
|
||||
* DOC: Update docs for heap-profiler functions (csilvers)
|
||||
* DOC: Clean up documentation around tcmalloc.slack_bytes (fikes)
|
||||
* DOC: Renamed README.windows to README_windows.txt (csilvers)
|
||||
* DOC: Update the NEWS file to be non-empty (csilvers)
|
||||
* PORTING: Fix windows addr2line and nm with proper rc code (csilvers)
|
||||
* PORTING: Add CycleClock and atomicops support for arm 5 (sanek)
|
||||
* PORTING: Improve PC finding on cygwin and redhat 7 (csilvers)
|
||||
* PORTING: speed up function-patching under windows (csilvers)
|
||||
|
||||
Tue Jan 19 14:46:12 2010 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 1.5 release
|
||||
* Add tc_set_new_mode (willchan)
|
||||
* Make memalign functions + realloc respect tc_set_new_mode (willchan)
|
||||
* Add ReleaseToSystem(num_bytes) (kash)
|
||||
* Handle zero-length symbols a bit better in pprof (csilvers)
|
||||
* Prefer __environ to /proc/self/environ in cpu profiler (csilvers)
|
||||
* Add HEAP_CHECK_MAX_LEAKS flag to control #leaks to report (glider)
|
||||
* Add two new numeric pageheap properties to MallocExtension (fikes)
|
||||
* Print alloc size when mmap fails (hakon)
|
||||
* Add ITIMER_REAL support to cpu profiler (csilvers, nabeelmian)
|
||||
* Speed up symbolizer in heap-checker reporting (glider)
|
||||
* Speed up futexes with FUTEX_PRIVATE_FLAG (m3b)
|
||||
* Speed up tcmalloc but doing better span coalescing (sanjay)
|
||||
* Better support for different wget's and addr2maps in pprof (csilvres)
|
||||
* Implement a nothrow version of delete and delete[] (csilvers)
|
||||
* BUGFIX: fix a race on module_libcs[i] in windows patching (csilvers)
|
||||
* BUGFIX: Fix debugallocation to call cpp_alloc for new (willchan)
|
||||
* BUGFIX: A simple bugfix for --raw mode (mrabkin)
|
||||
* BUGFIX: Fix C shims to actually be valid C (csilvers)
|
||||
* BUGFIX: Fix recursively-unmapped-region accounting (ppluzhnikov)
|
||||
* BUGFIX: better distinguish real and fake vdso (ppluzhnikov)
|
||||
* WINDOWS: replace debugmodule with more reliable psai (andrey)
|
||||
* PORTING: Add .bundle as another shared library extension (csilvers)
|
||||
* PORTING: Fixed a typo bug in the ocnfigure PRIxx m4 macro (csilvers)
|
||||
* PORTING: Augment sysinfo to work on 64-bit OS X (csilvers)
|
||||
* PORTING: Use sys/ucontext.h to fix compiing on OS X 10.6 (csilvers)
|
||||
* PORTING: Fix sysinfo libname reporting for solaris x86 (jeffrey)
|
||||
* PORTING: Use libunwind for i386 when using --omitfp (ppluzhnikov)
|
||||
|
||||
Thu Sep 10 13:51:15 2009 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 1.4 release
|
||||
* Add debugallocation library, to catch memory leaks, stomping, etc
|
||||
* Add --raw mode to allow for delayed processing of pprof files
|
||||
* Use less memory when reading CPU profiles
|
||||
* New environment variables to control kernel-allocs (sbrk, memfs, etc)
|
||||
* Add MarkThreadBusy(): performance improvement
|
||||
* Remove static thread-cache-size code; all is dynamic now
|
||||
* Add new HiddenPointer class to heap checker
|
||||
* BUGFIX: pvalloc(0) allocates now (found by new debugalloc library)
|
||||
* BUGFIX: valloc test (not implementation) no longer overruns memory
|
||||
* BUGFIX: GetHeapProfile no longer deadlocks
|
||||
* BUGFIX: Support unmapping memory regions before main
|
||||
* BUGFIX: Fix some malloc-stats formatting
|
||||
* BUGFIX: Don't crash as often when freeing libc-allocated memory
|
||||
* BUGFIX: Deal better with incorrect PPROF_PATH when symbolizing
|
||||
* BUGFIX: weaken new/delete/etc in addition to malloc/free/etc
|
||||
* BUGFIX: Fix return value of GetAllocatedSize
|
||||
* PORTING: Fix mmap-#define problem on some 64-bit systems
|
||||
* PORTING: Call ranlib again (some OS X versions need it)
|
||||
* PORTING: Fix a leak when building with LLVM
|
||||
* PORTING: Remove some unneeded bash-ishs from testing scripts
|
||||
* WINDOWS: Support library unloading as well as loading
|
||||
* WINDOWS/BUGFIX: Set page to 'xrw' instead of 'rw' when patching
|
||||
|
||||
Tue Jun 9 18:19:06 2009 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 1.3 release
|
||||
* Provide our own name for memory functions: tc_malloc, etc (csilvers)
|
||||
* Weaken memory-alloc functions so user can override them (csilvers)
|
||||
* Remove meaningless delete(nothrow) and delete[](nothrow) (csilvers)
|
||||
* BUILD: replace clever libtcmalloc/profiler.a with a new .a (csilvers)
|
||||
* PORTING: improve windows port by using google spinlocks (csilvers)
|
||||
* PORTING: Fix RedHat 9 memory allocation in heapchecker (csilvers)
|
||||
* PORTING: Rename OS_WINDOWS macro to PLATFORM_WINDOWS (mbelshe)
|
||||
* PORTING/BUGFIX: Make sure we don't clobber GetLastError (mbelshe)
|
||||
* BUGFIX: get rid of useless data for callgrind (weidenrinde)
|
||||
* BUGFIX: Modify windows patching to deadlock sometimes (csilvers)
|
||||
* BUGFIX: an improved fix for hook handling during fork (csilvers)
|
||||
* BUGFIX: revamp profiler_unittest.sh, which was very broken (csilvers)
|
||||
|
||||
Fri Apr 17 16:40:48 2009 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 1.2 release
|
||||
* Allow large_alloc_threshold=0 to turn it off entirely (csilvers)
|
||||
* Die more helpfully when out of memory for internal data (csilvers)
|
||||
* Refactor profile-data gathering, add a new unittest (cgd, nabeelmian)
|
||||
* BUGFIX: fix rounding errors with static thread-size caches (addi)
|
||||
* BUGFIX: disable hooks better when forking in leak-checker (csilvers)
|
||||
* BUGFIX: fix realloc of crt pointers on windows (csilvers)
|
||||
* BUGFIX: do a better job of finding binaries in .sh tests (csilvers)
|
||||
* WINDOWS: allow overriding malloc/etc instead of patching (mbelshe)
|
||||
* PORTING: fix compilation error in a ppc-specific file (csilvers)
|
||||
* PORTING: deal with quirks in cygwin's /proc/self/maps (csilvers)
|
||||
* PORTING: use 'A' version of functions for ascii input (mbelshe)
|
||||
* PORTING: generate .so's on cygwin and mingw (ajenjo)
|
||||
* PORTING: disable profiler methods on cygwin (jperkins)
|
||||
* Updated autoconf version to 2.61 and libtool version to 1.5.26
|
||||
|
||||
Wed Mar 11 11:25:34 2009 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 1.1 release
|
||||
* Dynamically resize thread caches -- nice perf. improvement (kash)
|
||||
* Add VDSO support to give better stacktraces in linux (ppluzhnikov)
|
||||
* Improve heap-profiling sampling algorithm (ford)
|
||||
* Rewrite leak-checking code: should be faster and more robust (sanjay)
|
||||
* Use ps2 instead of ps for dot: better page cropping for gv (csilvers)
|
||||
* Disable malloc-failure warning messages by default (csilvers)
|
||||
* Update config/Makefile to disable tests on a per-OS basis (csilvers)
|
||||
* PORTING: Get perftools compiling under MSVC 7.1 again (csilvers)
|
||||
* PORTING: Get perftools compiling under cygwin again (csilvers)
|
||||
* PORTING: automatically set library flags for solaris x86 (csilvers)
|
||||
* Add TCMALLOC_SKIP_SBRK to mirror TCMALLOC_SKIP_MMAP (csilvers)
|
||||
* Add --enable flags to allow selective building (csilvers)
|
||||
* Put addr2line-pdb and nm-pdb in proper output directory (csilvers)
|
||||
* Remove deprecated DisableChecksIn (sanjay)
|
||||
* DOCUMENTATION: Document most MallocExtension routines (csilvers)
|
||||
|
||||
Tue Jan 6 13:58:56 2009 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 1.0 release
|
||||
* Exactly the same as 1.0rc2
|
||||
|
||||
Sun Dec 14 17:10:35 2008 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 1.0rc2 release
|
||||
* Fix compile error on 64-bit systems (casting ptr to int) (csilvers)
|
||||
|
||||
Thu Dec 11 16:01:32 2008 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 1.0rc1 release
|
||||
* Replace API for selectively disabling heap-checker in code (sanjay)
|
||||
* Add a pre-mmap hook (daven, adlr)
|
||||
* Add MallocExtension interface to set memory-releasing rate (fikes)
|
||||
* Augment pprof to allow any string ending in /pprof/profile (csilvers)
|
||||
* PORTING: Rewrite -- and fix -- malloc patching for windows (dvitek)
|
||||
* PORTING: Add nm-pdb and addr2line-pdb for use by pprof (dvitek)
|
||||
* PORTING: Improve cygwin and mingw support (jperkins, csilvers)
|
||||
* PORTING: Fix pprof for mac os x, other pprof improvements (csilvers)
|
||||
* PORTING: Fix some PPC bugs in our locking code (anton.blanchard)
|
||||
* A new unittest, smapling_test, to verify tcmalloc-profiles (csilvers)
|
||||
* Turn off TLS for gcc < 4.1.2, due to a TLS + -fPIC bug (csilvers)
|
||||
* Prefer __builtin_frame_address to assembly for stacktraces (nlewycky)
|
||||
* Separate tcmalloc.cc out into multiple files -- finally! (kash)
|
||||
* Make our locking code work with -fPIC on 32-bit x86 (aruns)
|
||||
* Fix an initialization-ordering bug for tcmalloc/profiling (csilvers)
|
||||
* Use "initial exec" model of TLS to speed up tcmalloc (csilvers)
|
||||
* Enforce 16-byte alignment for tcmalloc, for SSE (sanjay)
|
||||
|
||||
Tue Sep 23 08:56:31 2008 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 0.99.2 release
|
||||
* COMPILE FIX: add #include needed for FreeBSD and OS X (csilvers)
|
||||
|
||||
Sat Sep 20 09:37:18 2008 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 0.99.1 release
|
||||
* BUG FIX: look for nm, etc in /usr/bin, not /usr/crosstool (csilvers)
|
||||
|
||||
Thu Sep 18 16:00:27 2008 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 0.99 release
|
||||
* Add IsHeapProfileRunning (csilvers)
|
||||
* Add C shims for some of the C++ header files (csilvers)
|
||||
* Fix heap profile file clean-up logic (maxim)
|
||||
* Rename linuxthreads.c to .cc for better compiler support (csilvers)
|
||||
* Add source info to disassembly in pprof (sanjay)
|
||||
* Use open instead of fopen to avoid memory alloc (csilvers)
|
||||
* Disable malloc extensions when running under valgrind (kcc)
|
||||
* BUG FIX: Fix out-of-bound error by reordering a check (larryz)
|
||||
* Add Options struct to ProfileData (cgd)
|
||||
* Correct PC-handling of --base in pprof (csilvers)
|
||||
* Handle 1 function occurring twice in an image (sanjay)
|
||||
* Improve stack-data cleaning (maxim)
|
||||
* Use 'struct Foo' to make header C compatible (csilvers)
|
||||
* Add 'total' line to pprof --text (csilvers)
|
||||
* Pre-allocate buffer for heap-profiler to avoid OOM errors (csilvers)
|
||||
* Allow a few more env-settings to control tcmalloc (csilvers)
|
||||
* Document some of the issues involving thread-local storage (csilvers)
|
||||
* BUG FIX: Define strtoll and friends for windows (csilvers)
|
||||
|
||||
Mon Jun 9 16:47:03 2008 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 0.98 release
|
||||
* Add ProfilerStartWithOptions() (cgd)
|
||||
* Change tcmalloc_minimal to not do any stack-tracing at all (csilvers)
|
||||
* Prefer mmap to sbrk for 64-buit debug mode (sanjay)
|
||||
* Fix accounting for some tcmalloc stats (sanjay)
|
||||
* Use setrlimit() to keep unittests from killing the machine (odo)
|
||||
* Fix a bug when sbrk-ing near address 4G (csilvers)
|
||||
* Make MallocHook thread-safe (jyasskin)
|
||||
* Fix windows build for MemoryBarrier (jyasskin)
|
||||
* Fix CPU-profiler docs to mention correct libs (csilvers)
|
||||
* Fix for GetHeapProfile() when heap-profiling is off (maxim)
|
||||
* Avoid realloc resizing ping-pongs using hysteresis (csilvers)
|
||||
* Add --callgrind output support to pprof (klimek)
|
||||
* Fix profiler.h and heap-profiler.h to be C-compatible (csilvers)
|
||||
* Break malloc_hook.h into two parts to reduce dependencies (csilvers)
|
||||
* Better handle systems that don't implement mmap (csilvers)
|
||||
* PORTING: disable system_alloc_unittest for msvc (csilvers)
|
||||
* PORTING: Makefile tweaks to build better on cygwin (csilvers)
|
||||
|
||||
Mon Apr 21 15:20:52 2008 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 0.97 release
|
||||
* Refactor GetHeapProfile to avoid using malloc (maxim)
|
||||
* Fix heap-checker and heap-profiler hook interactions (maxim)
|
||||
* Fix a data race in MemoryRegionMap::Lock (jyasskin)
|
||||
* Improve thread-safety of leak checker (maxim)
|
||||
* Fix mmap profile to no longer deadlock (maxim)
|
||||
* Fix rpm to have devel package depend on non-devel (csilvers)
|
||||
* PORTING: Fix clock-speed detection for Mac OS X (csilvers)
|
||||
|
||||
Tue Mar 18 14:30:44 2008 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 0.96 release
|
||||
* major atomicops rewrite; fixed atomic ops code for linux/ppc (vchen)
|
||||
* nix the stacktrace library; now build structure is simpler (csilvers)
|
||||
* Speed up heap-checker, and reduce extraneous logging (maxim)
|
||||
* Improve itimer code for NPTL case (cgd)
|
||||
* Add source code annotations for use by valgrind, etc (kcc)
|
||||
* PORTING: Fix high resolution timers for Mac OS X (adlr)
|
||||
|
||||
Tue Feb 19 12:01:31 2008 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 0.95.1 release (bugfix release)
|
||||
* x86_64 compile-fix: nix pread64 and pwrite64 (csilvers)
|
||||
* more heap-checker debug logging (maxim)
|
||||
* minor improvement to x86_64 CycleClock (gpike)
|
||||
|
||||
Tue Feb 12 12:28:32 2008 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 0.95 release
|
||||
* Better -- not perfect -- support for linux-ppc (csilvers)
|
||||
* Fix race condition in libunwind stacktrace (aruns)
|
||||
* Speed up x86 spinlock locking (m3b)
|
||||
* Improve heap-checker performance (maxim)
|
||||
* Heap checker traverses more ptrs inside heap-alloced objects (maxim)
|
||||
* Remove deprecated ProfilerThreadState function (cgd)
|
||||
* Update libunwind documentation for statically linked binaries (aruns)
|
||||
|
||||
Mon Dec 3 23:51:54 2007 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 0.94.1 release (bugfix release)
|
||||
* Fix missing #includes for x86_64 compile using libunwind (csilvers)
|
||||
|
||||
Thu Nov 29 07:59:43 2007 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 0.94 release
|
||||
* PORTING: MinGW/Msys support -- runs same code as MSVC does (csilvers)
|
||||
* PORTING: Add NumCPUs support for Mac OS X (csilvers)
|
||||
* Work around a sscanf bug in glibc(?) (waldemar)
|
||||
* Fix Windows MSVC bug triggered by thread deletion (csilvers)
|
||||
* Fix bug that triggers in MSVC /O2: missing volatile (gpike)
|
||||
* March-of-time support: quiet warnings/errors for gcc 4.2, OS X 10.5
|
||||
* Modify pprof so it works without nm: useful for windows (csilvers)
|
||||
* pprof: Support filtering for CPU profiles (cgd)
|
||||
* Bugfix: have realloc report to hooks in all situations (maxim)
|
||||
* Speed improvement: replace slow memcpy with std::copy (soren)
|
||||
* Speed: better iterator efficiency in RecordRegionRemoval (soren)
|
||||
* Speed: minor speed improvements via better bitfield alignment (gpike)
|
||||
* Documentation: add documentation of binary profile output (cgd)
|
||||
|
||||
Fri Aug 17 12:32:56 2007 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 0.93 release
|
||||
* PORTING: everything compiles on Solaris, OS X, FreeBSD (see INSTALL)
|
||||
* PORTING: cpu-profiler works on most platforms (much better GetPC())
|
||||
* PORTING: heap-profiler works on most platforms
|
||||
* PORTING: improved windows support, including release builds
|
||||
* No longer build or run ptmalloc tests by default
|
||||
* Add support for using memfs filesystem to allocate memory in linux
|
||||
* WINDOWS: give debug library and release library different names
|
||||
|
||||
Tue Jul 17 22:26:27 2007 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 0.92 release
|
||||
* PERFORMANCE: use a packed cache to speed up tcmalloc
|
||||
* PORTING: preliminary windows support! (see README.windows)
|
||||
* PORTING: better support for solaris, OS X, FreeBSD (see INSTALL)
|
||||
* Envvar support for running the heap-checker under gdb
|
||||
* Add weak declarations to maybe_threads to fix no-pthreads compile bugs
|
||||
* Some 64bit fixes, especially with pprof
|
||||
* Better heap-checker support for some low-level allocations
|
||||
* Fix bug where heap-profiles would sometimes get truncated
|
||||
* New documentation about how to handle common heap leak situations
|
||||
* Use computed includes for hash_map/set: easier config
|
||||
* Added all used .m4 templates to the distribution
|
||||
|
||||
Wed Apr 18 16:43:55 2007 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 0.91 release
|
||||
* Brown-paper-bag bugfix: compilation error on some x86-64 machines
|
||||
|
||||
Fri Apr 13 14:50:51 2007 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 0.90 release
|
||||
* (As the version-number jump hints, this is a major new release:
|
||||
almost every piece of functionality was rewritten. I can't do
|
||||
justice to all the changes, but will concentrate on highlights.)
|
||||
*** USER-VISIBLE CHANGES:
|
||||
* Ability to "release" unused memory added to tcmalloc
|
||||
* Exposed more tweaking knobs via environment variables (see docs)
|
||||
* pprof tries harder to map addresses to functions
|
||||
* tcmalloc_minimal compiles and runs on FreeBSD 6.0 and Solaris 10
|
||||
*** INTERNAL CHANGES:
|
||||
* Much better 64-bit support
|
||||
* Better multiple-processor support (e.g. multicore contention tweaks)
|
||||
* Support for recent kernel ABI changes (e.g. new arg to mremap)
|
||||
* Addition of spinlocks to tcmalloc to reduce contention cost
|
||||
* Speed up tcmalloc by using __thread on systems that support TLS
|
||||
* Total redesign of heap-checker to improve liveness checking
|
||||
* More portable stack-frame analysis -- no more hard-coded constants!
|
||||
* Disentangled heap-profiler code and heap-checker code
|
||||
* Several new unittests to test, e.g., thread-contention costs
|
||||
* Lots of small (but important!) bug fixes: e.g., fixing GetPC on amd64
|
||||
*** KNOWN PROBLEMS:
|
||||
* CPU-profiling may crash on x86_64 (64-bit) systems. See the README
|
||||
* Profiling/heap-checking may deadlock on x86_64 systems. See README
|
||||
|
||||
Wed Jun 14 15:11:14 2006 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 0.8 release
|
||||
* Experimental support for remote profiling added to pprof (many)
|
||||
* Fixed race condition in ProfileData::FlushTable (etune)
|
||||
* Better support for weird /proc maps (maxim, mec)
|
||||
* Fix heap-checker interaction with gdb (markus)
|
||||
* Better 64-bit support in pprof (aruns)
|
||||
* Reduce scavenging cost in tcmalloc by capping NumMoveSize (sanjay)
|
||||
* Cast syscall(SYS_mmap); works on more 64-bit systems now (menage)
|
||||
* Document the text output of pprof! (csilvers)
|
||||
* Better compiler support for no-THREADS and for old compilers (csilvers)
|
||||
* Make libunwind the default stack unwinder for x86-64 (aruns)
|
||||
* Somehow the COPYING file got erased. Regenerate it (csilvers)
|
||||
|
||||
Thu Apr 13 20:59:09 2006 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 0.7 release
|
||||
* Major rewrite of thread introspection for new kernels (markus)
|
||||
* Major rewrite of heap-checker to use new thread tools (maxim)
|
||||
* Add proper support for following data in thread registers (maxim)
|
||||
* Syscall support for older kernels, including _syscall6 (markus)
|
||||
* Support PIC mode (markus, mbland, iant)
|
||||
* Better support for running in non-threaded contexts (csilvers)
|
||||
|
||||
Fri Jan 27 14:04:27 2006 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 0.6 release
|
||||
* More sophisticated stacktrace usage, possibly using libunwind (aruns)
|
||||
* Update pprof to handle 64-bit profiles (dehnert)
|
||||
* Fix GetStackTrace to correctly return top stackframe (sanjay)
|
||||
* Add ANSI compliance for new and new[], including new_handler (jkearney)
|
||||
* More accuracy by reading ELF files directly rather than objdump (mec)
|
||||
* Add readline support for pprof (addi)
|
||||
* Add #includes for PPC (csilvers)
|
||||
* New PC-detection routine for ibook powerpc (asbestoshead)
|
||||
* Vastly improved tcmalloc unittest (csilvers)
|
||||
* Move documentation from /usr/doc to /usr/share/doc
|
||||
|
||||
Mon Nov 14 17:28:59 2005 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 0.5 release
|
||||
* Add va_start/va_end calls around vsnprintf() (csilvers)
|
||||
* Write our own __syscall_return(), since it's not defined
|
||||
consistently on all 64-bit linux distros (markus)
|
||||
|
||||
Wed Oct 26 15:19:16 2005 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 0.4 release
|
||||
* Decrease fragmentation in tcmalloc (lefevere)
|
||||
* Support for ARM in some of the thread-specific code (markus)
|
||||
* Turn off heap-checker for statically-linked binaries, which
|
||||
cause error leak reports now (etune)
|
||||
* Many pprof improvements, including a command-line interface (jeff)
|
||||
* CPU profiling now automatically affects all threads in linux 2.6.
|
||||
(Kernel bugs break CPU profiling and threads in linux 2.4 a bit.)
|
||||
ProfilerEnable() and ProfilerDisable() are deprecated. (sanjay)
|
||||
* tcmalloc now correctly intercepts memalign (m3b, maxim)
|
||||
* Syntax fix: added missing va_end()s. Helps non-gcc compiling (etune)
|
||||
* Fixed a few coredumper bugs: race condition after PTRACE_DETACH,
|
||||
ignore non-aligned stackframe pointers (markus, menage)
|
||||
* 64-bit cleanup, especially for spinlock code (etune) and mmap (sanjay)
|
||||
* Better support for finding threads in linux (markus)
|
||||
* tcmalloc now tracks those stack traces that allocate memory (sanjay)
|
||||
* Work around a weird setspecific problem (sanjay)
|
||||
* Fix tcmalloc overflow problems when an alloc is close to 2G/4G (sanjay)
|
||||
|
||||
Fri Jun 24 18:02:26 2005 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 0.3 release
|
||||
* Add missing errno include for one of the unittests (csilvers)
|
||||
* Reduce tcmalloc startup memory from 5M to 256K (sanjay)
|
||||
* Add support for mallopt() and mallinfo (sanjay)
|
||||
* Improve stacktrace's performance on some 64-bit systems (etune)
|
||||
* Improve the stacktrace unittest (etune)
|
||||
|
||||
Tue May 31 08:14:38 2005 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: version 0.2 release
|
||||
* Use mmap2() instead of mmap(), to map more memory (menage)
|
||||
* Do correct pthread-local checking in heap-checker! (maxim)
|
||||
* Avoid overflow on 64-bit machines in pprof (sanjay)
|
||||
* Add a few more GetPC() functions, including for AMD (csilvers)
|
||||
* Better method for overriding pthread functions (menage)
|
||||
* (Hacky) fix to avoid overwriting profile files after fork() (csilvers)
|
||||
* Crashing bugfix involving dumping heaps on small-stack threads (tudor)
|
||||
* Allow library versions with letters at the end (csilvers)
|
||||
* Config fixes for systems that don't define PATH_MAX (csilvers)
|
||||
* Confix fixes so we no longer need config.h after install (csilvers)
|
||||
* Fix to pprof to correctly read very big cpu profiles (csilvers)
|
||||
* Fix to pprof to deal with new commandline flags in modern gv's
|
||||
* Better error reporting when we can't access /proc/maps (etune)
|
||||
* Get rid of the libc-preallocate code (which could crash on some
|
||||
systems); no longer needed with local-threads fix (csilvers)
|
||||
|
||||
Tue Feb 8 09:57:17 2005 Google Inc. <opensource@google.com>
|
||||
|
||||
* google-perftools: initial release:
|
||||
The google-perftools package contains some utilities to improve
|
||||
and analyze the performance of C++ programs. This includes an
|
||||
optimized thread-caching malloc() and cpu and heap profiling
|
||||
utilities.
|
564
trunk/3rdparty/gperftools-2-fit/INSTALL
vendored
Normal file
|
@ -0,0 +1,564 @@
|
|||
Copyright 1994, 1995, 1996, 1999, 2000, 2001, 2002 Free Software
|
||||
Foundation, Inc.
|
||||
|
||||
This file is free documentation; the Free Software Foundation gives
|
||||
unlimited permission to copy, distribute and modify it.
|
||||
|
||||
|
||||
Perftools-Specific Install Notes
|
||||
================================
|
||||
|
||||
*** Building from source repository
|
||||
|
||||
As of 2.1 gperftools does not have configure and other autotools
|
||||
products checked into it's source repository. This is common practice
|
||||
for projects using autotools.
|
||||
|
||||
NOTE: Source releases (.tar.gz that you download from
|
||||
code.google.com/p/gperftools) still have all required files just as
|
||||
before. Nothing has changed w.r.t. building from .tar.gz releases.
|
||||
|
||||
But, in order to build gperftools checked out from subversion
|
||||
repository you need to have autoconf, automake and libtool
|
||||
installed. And before running ./configure you have to generate it (and
|
||||
a bunch of other files) by running ./autogen.sh script. That script
|
||||
will take care of calling correct autotools programs in correct order.
|
||||
|
||||
If you're maintainer then it's business as usual too. Just run make
|
||||
dist (or, preferably, make distcheck) and it'll produce .tar.gz or
|
||||
.tar.bz2 with all autotools magic already included. So that users can
|
||||
build our software without having autotools.
|
||||
|
||||
|
||||
*** NOTE FOR 64-BIT LINUX SYSTEMS
|
||||
|
||||
The glibc built-in stack-unwinder on 64-bit systems has some problems
|
||||
with the perftools libraries. (In particular, the cpu/heap profiler
|
||||
may be in the middle of malloc, holding some malloc-related locks when
|
||||
they invoke the stack unwinder. The built-in stack unwinder may call
|
||||
malloc recursively, which may require the thread to acquire a lock it
|
||||
already holds: deadlock.)
|
||||
|
||||
For that reason, if you use a 64-bit system, we strongly recommend you
|
||||
install libunwind before trying to configure or install gperftools.
|
||||
libunwind can be found at
|
||||
|
||||
http://download.savannah.gnu.org/releases/libunwind/libunwind-0.99-beta.tar.gz
|
||||
|
||||
Even if you already have libunwind installed, you should check the
|
||||
version. Versions older than this will not work properly; too-new
|
||||
versions introduce new code that does not work well with perftools
|
||||
(because libunwind can call malloc, which will lead to deadlock).
|
||||
|
||||
There have been reports of crashes with libunwind 0.99 (see
|
||||
http://code.google.com/p/gperftools/issues/detail?id=374).
|
||||
Alternately, you can use a more recent libunwind (e.g. 1.0.1) at the
|
||||
cost of adding a bit of boilerplate to your code. For details, see
|
||||
http://groups.google.com/group/google-perftools/msg/2686d9f24ac4365f
|
||||
|
||||
CAUTION: if you install libunwind from the url above, be aware that
|
||||
you may have trouble if you try to statically link your binary with
|
||||
perftools: that is, if you link with 'gcc -static -lgcc_eh ...'.
|
||||
This is because both libunwind and libgcc implement the same C++
|
||||
exception handling APIs, but they implement them differently on
|
||||
some platforms. This is not likely to be a problem on ia64, but
|
||||
may be on x86-64.
|
||||
|
||||
Also, if you link binaries statically, make sure that you add
|
||||
-Wl,--eh-frame-hdr to your linker options. This is required so that
|
||||
libunwind can find the information generated by the compiler
|
||||
required for stack unwinding.
|
||||
|
||||
Using -static is rare, though, so unless you know this will affect
|
||||
you it probably won't.
|
||||
|
||||
If you cannot or do not wish to install libunwind, you can still try
|
||||
to use the built-in stack unwinder. The built-in stack unwinder
|
||||
requires that your application, the tcmalloc library, and system
|
||||
libraries like libc, all be compiled with a frame pointer. This is
|
||||
*not* the default for x86-64.
|
||||
|
||||
If you are on x86-64 system, know that you have a set of system
|
||||
libraries with frame-pointers enabled, and compile all your
|
||||
applications with -fno-omit-frame-pointer, then you can enable the
|
||||
built-in perftools stack unwinder by passing the
|
||||
--enable-frame-pointers flag to configure.
|
||||
|
||||
Even with the use of libunwind, there are still known problems with
|
||||
stack unwinding on 64-bit systems, particularly x86-64. See the
|
||||
"64-BIT ISSUES" section in README.
|
||||
|
||||
If you encounter problems, try compiling perftools with './configure
|
||||
--enable-frame-pointers'. Note you will need to compile your
|
||||
application with frame pointers (via 'gcc -fno-omit-frame-pointer
|
||||
...') in this case.
|
||||
|
||||
|
||||
*** TCMALLOC LARGE PAGES: TRADING TIME FOR SPACE
|
||||
|
||||
You can set a compiler directive that makes tcmalloc faster, at the
|
||||
cost of using more space (due to internal fragmentation).
|
||||
|
||||
Internally, tcmalloc divides its memory into "pages." The default
|
||||
page size is chosen to minimize memory use by reducing fragmentation.
|
||||
The cost is that keeping track of these pages can cost tcmalloc time.
|
||||
We've added a new flag to tcmalloc that enables a larger page size.
|
||||
In general, this will increase the memory needs of applications using
|
||||
tcmalloc. However, in many cases it will speed up the applications
|
||||
as well, particularly if they allocate and free a lot of memory. We've
|
||||
seen average speedups of 3-5% on Google applications.
|
||||
|
||||
To build libtcmalloc with large pages you need to use the
|
||||
--with-tcmalloc-pagesize=ARG configure flag, e.g.:
|
||||
|
||||
./configure <other flags> --with-tcmalloc-pagesize=32
|
||||
|
||||
The ARG argument can be 4, 8, 16, 32, 64, 128 or 256 which sets the
|
||||
internal page size to 4K, 8K, 16K, 32K, 64K, 128K and 256K respectively.
|
||||
The default is 8K.
|
||||
|
||||
|
||||
*** SMALL TCMALLOC CACHES: TRADING SPACE FOR TIME
|
||||
|
||||
You can set a compiler directive that makes tcmalloc use less memory
|
||||
for overhead, at the cost of some time.
|
||||
|
||||
Internally, tcmalloc keeps information about some of its internal data
|
||||
structures in a cache. This speeds memory operations that need to
|
||||
access this internal data. We've added a new, experimental flag to
|
||||
tcmalloc that reduces the size of this cache, decresaing the memory
|
||||
needs of applications using tcmalloc.
|
||||
|
||||
This feature is still very experimental; it's not even a configure
|
||||
flag yet. To build libtcmalloc with smaller internal caches, run
|
||||
|
||||
./configure <normal flags> CXXFLAGS=-DTCMALLOC_SMALL_BUT_SLOW
|
||||
|
||||
(or add -DTCMALLOC_SMALL_BUT_SLOW to your existing CXXFLAGS argument).
|
||||
|
||||
|
||||
*** NOTE FOR ___tls_get_addr ERROR
|
||||
|
||||
When compiling perftools on some old systems, like RedHat 8, you may
|
||||
get an error like this:
|
||||
___tls_get_addr: symbol not found
|
||||
|
||||
This means that you have a system where some parts are updated enough
|
||||
to support Thread Local Storage, but others are not. The perftools
|
||||
configure script can't always detect this kind of case, leading to
|
||||
that error. To fix it, just comment out the line
|
||||
#define HAVE_TLS 1
|
||||
in your config.h file before building.
|
||||
|
||||
|
||||
*** TCMALLOC AND DLOPEN
|
||||
|
||||
To improve performance, we use the "initial exec" model of Thread
|
||||
Local Storage in tcmalloc. The price for this is the library will not
|
||||
work correctly if it is loaded via dlopen(). This should not be a
|
||||
problem, since loading a malloc-replacement library via dlopen is
|
||||
asking for trouble in any case: some data will be allocated with one
|
||||
malloc, some with another. If, for some reason, you *do* need to use
|
||||
dlopen on tcmalloc, the easiest way is to use a version of tcmalloc
|
||||
with TLS turned off; see the ___tls_get_addr note above.
|
||||
|
||||
|
||||
*** COMPILING ON NON-LINUX SYSTEMS
|
||||
|
||||
Perftools has been tested on the following systems:
|
||||
FreeBSD 6.0 (x86)
|
||||
FreeBSD 8.1 (x86_64)
|
||||
Linux CentOS 5.5 (x86_64)
|
||||
Linux Debian 4.0 (PPC)
|
||||
Linux Debian 5.0 (x86)
|
||||
Linux Fedora Core 3 (x86)
|
||||
Linux Fedora Core 4 (x86)
|
||||
Linux Fedora Core 5 (x86)
|
||||
Linux Fedora Core 6 (x86)
|
||||
Linux Fedora Core 13 (x86_64)
|
||||
Linux Fedora Core 14 (x86_64)
|
||||
Linux RedHat 9 (x86)
|
||||
Linux Slackware 13 (x86_64)
|
||||
Linux Ubuntu 6.06.1 (x86)
|
||||
Linux Ubuntu 6.06.1 (x86_64)
|
||||
Linux Ubuntu 10.04 (x86)
|
||||
Linux Ubuntu 10.10 (x86_64)
|
||||
Mac OS X 10.3.9 (Panther) (PowerPC)
|
||||
Mac OS X 10.4.8 (Tiger) (PowerPC)
|
||||
Mac OS X 10.4.8 (Tiger) (x86)
|
||||
Mac OS X 10.5 (Leopard) (x86)
|
||||
Mac OS X 10.6 (Snow Leopard) (x86)
|
||||
Solaris 10 (x86_64)
|
||||
Windows XP, Visual Studio 2003 (VC++ 7.1) (x86)
|
||||
Windows XP, Visual Studio 2005 (VC++ 8) (x86)
|
||||
Windows XP, Visual Studio 2005 (VC++ 9) (x86)
|
||||
Windows XP, Visual Studio 2005 (VC++ 10) (x86)
|
||||
Windows XP, MinGW 5.1.3 (x86)
|
||||
Windows XP, Cygwin 5.1 (x86)
|
||||
|
||||
It works in its full generality on the Linux systems
|
||||
tested (though see 64-bit notes above). Portions of perftools work on
|
||||
the other systems. The basic memory-allocation library,
|
||||
tcmalloc_minimal, works on all systems. The cpu-profiler also works
|
||||
fairly widely. However, the heap-profiler and heap-checker are not
|
||||
yet as widely supported. In general, the 'configure' script will
|
||||
detect what OS you are building for, and only build the components
|
||||
that work on that OS.
|
||||
|
||||
Note that tcmalloc_minimal is perfectly usable as a malloc/new
|
||||
replacement, so it is possible to use tcmalloc on all the systems
|
||||
above, by linking in libtcmalloc_minimal.
|
||||
|
||||
** FreeBSD:
|
||||
|
||||
The following binaries build and run successfully (creating
|
||||
libtcmalloc_minimal.so and libprofile.so in the process):
|
||||
% ./configure
|
||||
% make tcmalloc_minimal_unittest tcmalloc_minimal_large_unittest \
|
||||
addressmap_unittest atomicops_unittest frag_unittest \
|
||||
low_level_alloc_unittest markidle_unittest memalign_unittest \
|
||||
packed_cache_test stacktrace_unittest system_alloc_unittest \
|
||||
thread_dealloc_unittest profiler_unittest.sh
|
||||
% ./tcmalloc_minimal_unittest # to run this test
|
||||
% [etc] # to run other tests
|
||||
|
||||
Three caveats: first, frag_unittest tries to allocate 400M of memory,
|
||||
and if you have less virtual memory on your system, the test may
|
||||
fail with a bad_alloc exception.
|
||||
|
||||
Second, profiler_unittest.sh sometimes fails in the "fork" test.
|
||||
This is because stray SIGPROF signals from the parent process are
|
||||
making their way into the child process. (This may be a kernel
|
||||
bug that only exists in older kernels.) The profiling code itself
|
||||
is working fine. This only affects programs that call fork(); for
|
||||
most programs, the cpu profiler is entirely safe to use.
|
||||
|
||||
Third, perftools depends on /proc to get shared library
|
||||
information. If you are running a FreeBSD system without proc,
|
||||
perftools will not be able to map addresses to functions. Some
|
||||
unittests will fail as a result.
|
||||
|
||||
Finally, the new test introduced in perftools-1.2,
|
||||
profile_handler_unittest, fails on FreeBSD. It has something to do
|
||||
with how the itimer works. The cpu profiler test passes, so I
|
||||
believe the functionality is correct and the issue is with the test
|
||||
somehow. If anybody is an expert on itimers and SIGPROF in
|
||||
FreeBSD, and would like to debug this, I'd be glad to hear the
|
||||
results!
|
||||
|
||||
libtcmalloc.so successfully builds, and the "advanced" tcmalloc
|
||||
functionality all works except for the leak-checker, which has
|
||||
Linux-specific code:
|
||||
% make heap-profiler_unittest.sh maybe_threads_unittest.sh \
|
||||
tcmalloc_unittest tcmalloc_both_unittest \
|
||||
tcmalloc_large_unittest # THESE WORK
|
||||
% make -k heap-checker_unittest.sh \
|
||||
heap-checker-death_unittest.sh # THESE DO NOT
|
||||
|
||||
Note that unless you specify --enable-heap-checker explicitly,
|
||||
'make' will not build the heap-checker unittests on a FreeBSD
|
||||
system.
|
||||
|
||||
I have not tested other *BSD systems, but they are probably similar.
|
||||
|
||||
** Mac OS X:
|
||||
|
||||
I've tested OS X 10.5 [Leopard], OS X 10.4 [Tiger] and OS X 10.3
|
||||
[Panther] on both intel (x86) and PowerPC systems. For Panther
|
||||
systems, perftools does not work at all: it depends on a header
|
||||
file, OSAtomic.h, which is new in 10.4. (It's possible to get the
|
||||
code working for Panther/i386 without too much work; if you're
|
||||
interested in exploring this, drop an e-mail.)
|
||||
|
||||
For the other seven systems, the binaries and libraries that
|
||||
successfully build are exactly the same as for FreeBSD. See that
|
||||
section for a list of binaries and instructions on building them.
|
||||
|
||||
In addition, it appears OS X regularly fails profiler_unittest.sh
|
||||
in the "thread" test (in addition to occassionally failing in the
|
||||
"fork" test). It looks like OS X often delivers the profiling
|
||||
signal to the main thread, even when it's sleeping, rather than
|
||||
spawned threads that are doing actual work. If anyone knows
|
||||
details of how OS X handles SIGPROF (via setitimer()) events with
|
||||
threads, and has insight into this problem, please send mail to
|
||||
google-perftools@googlegroups.com.
|
||||
|
||||
** Solaris 10 x86:
|
||||
|
||||
I've only tested using the GNU C++ compiler, not the Sun C++
|
||||
compiler. Using g++ requires setting the PATH appropriately when
|
||||
configuring.
|
||||
|
||||
% PATH=${PATH}:/usr/sfw/bin/:/usr/ccs/bin ./configure
|
||||
% PATH=${PATH}:/usr/sfw/bin/:/usr/ccs/bin make [...]
|
||||
|
||||
Again, the binaries and libraries that successfully build are
|
||||
exactly the same as for FreeBSD. (However, while libprofiler.so can
|
||||
be used to generate profiles, pprof is not very successful at
|
||||
reading them -- necessary helper programs like nm don't seem
|
||||
to be installed by default on Solaris, or perhaps are only
|
||||
installed as part of the Sun C++ compiler package.) See that
|
||||
section for a list of binaries, and instructions on building them.
|
||||
|
||||
** Windows (MSVC, Cygwin, and MinGW):
|
||||
|
||||
Work on Windows is rather preliminary: only tcmalloc_minimal is
|
||||
supported.
|
||||
|
||||
We haven't found a good way to get stack traces in release mode on
|
||||
windows (that is, when FPO is enabled), so the heap profiling may
|
||||
not be reliable in that case. Also, heap-checking and CPU profiling
|
||||
do not yet work at all. But as in other ports, the basic tcmalloc
|
||||
library functionality, overriding malloc and new and such (and even
|
||||
windows-specific functions like _aligned_malloc!), is working fine,
|
||||
at least with VC++ 7.1 (Visual Studio 2003) through VC++ 10.0,
|
||||
in both debug and release modes. See README.windows for
|
||||
instructions on how to install on Windows using Visual Studio.
|
||||
|
||||
Cygwin can compile some but not all of perftools. Furthermore,
|
||||
there is a problem with exception-unwinding in cygwin (it can call
|
||||
malloc, which can call the exception-unwinding-setup code, which
|
||||
can lead to an infinite loop). I've comitted a workaround to the
|
||||
exception unwinding problem, but it only works in debug mode and
|
||||
when statically linking in tcmalloc. I hope to have a more proper
|
||||
fix in a later release. To configure under cygwin, run
|
||||
|
||||
./configure --disable-shared CXXFLAGS=-g && make
|
||||
|
||||
Most of cygwin will compile (cygwin doesn't allow weak symbols, so
|
||||
the heap-checker and a few other pieces of functionality will not
|
||||
compile). 'make' will compile those libraries and tests that can
|
||||
be compiled. You can run 'make check' to make sure the basic
|
||||
functionality is working. I've heard reports that some versions of
|
||||
cygwin fail calls to pthread_join() with EINVAL, causing several
|
||||
tests to fail. If you have any insight into this, please mail
|
||||
google-perftools@googlegroups.com.
|
||||
|
||||
This Windows functionality is also available using MinGW and Msys,
|
||||
In this case, you can use the regular './configure && make'
|
||||
process. 'make install' should also work. The Makefile will limit
|
||||
itself to those libraries and binaries that work on windows.
|
||||
|
||||
|
||||
Basic Installation
|
||||
==================
|
||||
|
||||
These are generic installation instructions.
|
||||
|
||||
The `configure' shell script attempts to guess correct values for
|
||||
various system-dependent variables used during compilation. It uses
|
||||
those values to create a `Makefile' in each directory of the package.
|
||||
It may also create one or more `.h' files containing system-dependent
|
||||
definitions. Finally, it creates a shell script `config.status' that
|
||||
you can run in the future to recreate the current configuration, and a
|
||||
file `config.log' containing compiler output (useful mainly for
|
||||
debugging `configure').
|
||||
|
||||
It can also use an optional file (typically called `config.cache'
|
||||
and enabled with `--cache-file=config.cache' or simply `-C') that saves
|
||||
the results of its tests to speed up reconfiguring. (Caching is
|
||||
disabled by default to prevent problems with accidental use of stale
|
||||
cache files.)
|
||||
|
||||
If you need to do unusual things to compile the package, please try
|
||||
to figure out how `configure' could check whether to do them, and mail
|
||||
diffs or instructions to the address given in the `README' so they can
|
||||
be considered for the next release. If you are using the cache, and at
|
||||
some point `config.cache' contains results you don't want to keep, you
|
||||
may remove or edit it.
|
||||
|
||||
The file `configure.ac' (or `configure.in') is used to create
|
||||
`configure' by a program called `autoconf'. You only need
|
||||
`configure.ac' if you want to change it or regenerate `configure' using
|
||||
a newer version of `autoconf'.
|
||||
|
||||
The simplest way to compile this package is:
|
||||
|
||||
1. `cd' to the directory containing the package's source code and type
|
||||
`./configure' to configure the package for your system. If you're
|
||||
using `csh' on an old version of System V, you might need to type
|
||||
`sh ./configure' instead to prevent `csh' from trying to execute
|
||||
`configure' itself.
|
||||
|
||||
Running `configure' takes awhile. While running, it prints some
|
||||
messages telling which features it is checking for.
|
||||
|
||||
2. Type `make' to compile the package.
|
||||
|
||||
3. Optionally, type `make check' to run any self-tests that come with
|
||||
the package.
|
||||
|
||||
4. Type `make install' to install the programs and any data files and
|
||||
documentation.
|
||||
|
||||
5. You can remove the program binaries and object files from the
|
||||
source code directory by typing `make clean'. To also remove the
|
||||
files that `configure' created (so you can compile the package for
|
||||
a different kind of computer), type `make distclean'. There is
|
||||
also a `make maintainer-clean' target, but that is intended mainly
|
||||
for the package's developers. If you use it, you may have to get
|
||||
all sorts of other programs in order to regenerate files that came
|
||||
with the distribution.
|
||||
|
||||
Compilers and Options
|
||||
=====================
|
||||
|
||||
Some systems require unusual options for compilation or linking that
|
||||
the `configure' script does not know about. Run `./configure --help'
|
||||
for details on some of the pertinent environment variables.
|
||||
|
||||
You can give `configure' initial values for configuration parameters
|
||||
by setting variables in the command line or in the environment. Here
|
||||
is an example:
|
||||
|
||||
./configure CC=c89 CFLAGS=-O2 LIBS=-lposix
|
||||
|
||||
*Note Defining Variables::, for more details.
|
||||
|
||||
Compiling For Multiple Architectures
|
||||
====================================
|
||||
|
||||
You can compile the package for more than one kind of computer at the
|
||||
same time, by placing the object files for each architecture in their
|
||||
own directory. To do this, you must use a version of `make' that
|
||||
supports the `VPATH' variable, such as GNU `make'. `cd' to the
|
||||
directory where you want the object files and executables to go and run
|
||||
the `configure' script. `configure' automatically checks for the
|
||||
source code in the directory that `configure' is in and in `..'.
|
||||
|
||||
If you have to use a `make' that does not support the `VPATH'
|
||||
variable, you have to compile the package for one architecture at a
|
||||
time in the source code directory. After you have installed the
|
||||
package for one architecture, use `make distclean' before reconfiguring
|
||||
for another architecture.
|
||||
|
||||
Installation Names
|
||||
==================
|
||||
|
||||
By default, `make install' will install the package's files in
|
||||
`/usr/local/bin', `/usr/local/man', etc. You can specify an
|
||||
installation prefix other than `/usr/local' by giving `configure' the
|
||||
option `--prefix=PATH'.
|
||||
|
||||
You can specify separate installation prefixes for
|
||||
architecture-specific files and architecture-independent files. If you
|
||||
give `configure' the option `--exec-prefix=PATH', the package will use
|
||||
PATH as the prefix for installing programs and libraries.
|
||||
Documentation and other data files will still use the regular prefix.
|
||||
|
||||
In addition, if you use an unusual directory layout you can give
|
||||
options like `--bindir=PATH' to specify different values for particular
|
||||
kinds of files. Run `configure --help' for a list of the directories
|
||||
you can set and what kinds of files go in them.
|
||||
|
||||
If the package supports it, you can cause programs to be installed
|
||||
with an extra prefix or suffix on their names by giving `configure' the
|
||||
option `--program-prefix=PREFIX' or `--program-suffix=SUFFIX'.
|
||||
|
||||
Optional Features
|
||||
=================
|
||||
|
||||
Some packages pay attention to `--enable-FEATURE' options to
|
||||
`configure', where FEATURE indicates an optional part of the package.
|
||||
They may also pay attention to `--with-PACKAGE' options, where PACKAGE
|
||||
is something like `gnu-as' or `x' (for the X Window System). The
|
||||
`README' should mention any `--enable-' and `--with-' options that the
|
||||
package recognizes.
|
||||
|
||||
For packages that use the X Window System, `configure' can usually
|
||||
find the X include and library files automatically, but if it doesn't,
|
||||
you can use the `configure' options `--x-includes=DIR' and
|
||||
`--x-libraries=DIR' to specify their locations.
|
||||
|
||||
Specifying the System Type
|
||||
==========================
|
||||
|
||||
There may be some features `configure' cannot figure out
|
||||
automatically, but needs to determine by the type of machine the package
|
||||
will run on. Usually, assuming the package is built to be run on the
|
||||
_same_ architectures, `configure' can figure that out, but if it prints
|
||||
a message saying it cannot guess the machine type, give it the
|
||||
`--build=TYPE' option. TYPE can either be a short name for the system
|
||||
type, such as `sun4', or a canonical name which has the form:
|
||||
|
||||
CPU-COMPANY-SYSTEM
|
||||
|
||||
where SYSTEM can have one of these forms:
|
||||
|
||||
OS KERNEL-OS
|
||||
|
||||
See the file `config.sub' for the possible values of each field. If
|
||||
`config.sub' isn't included in this package, then this package doesn't
|
||||
need to know the machine type.
|
||||
|
||||
If you are _building_ compiler tools for cross-compiling, you should
|
||||
use the `--target=TYPE' option to select the type of system they will
|
||||
produce code for.
|
||||
|
||||
If you want to _use_ a cross compiler, that generates code for a
|
||||
platform different from the build platform, you should specify the
|
||||
"host" platform (i.e., that on which the generated programs will
|
||||
eventually be run) with `--host=TYPE'.
|
||||
|
||||
Sharing Defaults
|
||||
================
|
||||
|
||||
If you want to set default values for `configure' scripts to share,
|
||||
you can create a site shell script called `config.site' that gives
|
||||
default values for variables like `CC', `cache_file', and `prefix'.
|
||||
`configure' looks for `PREFIX/share/config.site' if it exists, then
|
||||
`PREFIX/etc/config.site' if it exists. Or, you can set the
|
||||
`CONFIG_SITE' environment variable to the location of the site script.
|
||||
A warning: not all `configure' scripts look for a site script.
|
||||
|
||||
Defining Variables
|
||||
==================
|
||||
|
||||
Variables not defined in a site shell script can be set in the
|
||||
environment passed to `configure'. However, some packages may run
|
||||
configure again during the build, and the customized values of these
|
||||
variables may be lost. In order to avoid this problem, you should set
|
||||
them in the `configure' command line, using `VAR=value'. For example:
|
||||
|
||||
./configure CC=/usr/local2/bin/gcc
|
||||
|
||||
will cause the specified gcc to be used as the C compiler (unless it is
|
||||
overridden in the site shell script).
|
||||
|
||||
`configure' Invocation
|
||||
======================
|
||||
|
||||
`configure' recognizes the following options to control how it
|
||||
operates.
|
||||
|
||||
`--help'
|
||||
`-h'
|
||||
Print a summary of the options to `configure', and exit.
|
||||
|
||||
`--version'
|
||||
`-V'
|
||||
Print the version of Autoconf used to generate the `configure'
|
||||
script, and exit.
|
||||
|
||||
`--cache-file=FILE'
|
||||
Enable the cache: use and save the results of the tests in FILE,
|
||||
traditionally `config.cache'. FILE defaults to `/dev/null' to
|
||||
disable caching.
|
||||
|
||||
`--config-cache'
|
||||
`-C'
|
||||
Alias for `--cache-file=config.cache'.
|
||||
|
||||
`--quiet'
|
||||
`--silent'
|
||||
`-q'
|
||||
Do not print messages saying which checks are being made. To
|
||||
suppress all normal output, redirect it to `/dev/null' (any error
|
||||
messages will still be shown).
|
||||
|
||||
`--srcdir=DIR'
|
||||
Look for the package's source code in directory DIR. Usually
|
||||
`configure' can determine that directory automatically.
|
||||
|
||||
`configure' also accepts some other, not widely useful, options. Run
|
||||
`configure --help' for more details.
|
1508
trunk/3rdparty/gperftools-2-fit/Makefile.am
vendored
Normal file
8288
trunk/3rdparty/gperftools-2-fit/Makefile.in
vendored
Normal file
1193
trunk/3rdparty/gperftools-2-fit/NEWS
vendored
Normal file
279
trunk/3rdparty/gperftools-2-fit/README
vendored
Normal file
|
@ -0,0 +1,279 @@
|
|||
gperftools
|
||||
----------
|
||||
(originally Google Performance Tools)
|
||||
|
||||
The fastest malloc we’ve seen; works particularly well with threads
|
||||
and STL. Also: thread-friendly heap-checker, heap-profiler, and
|
||||
cpu-profiler.
|
||||
|
||||
|
||||
OVERVIEW
|
||||
---------
|
||||
|
||||
gperftools is a collection of a high-performance multi-threaded
|
||||
malloc() implementation, plus some pretty nifty performance analysis
|
||||
tools.
|
||||
|
||||
gperftools is distributed under the terms of the BSD License. Join our
|
||||
mailing list at gperftools@googlegroups.com for updates:
|
||||
https://groups.google.com/forum/#!forum/gperftools
|
||||
|
||||
gperftools was original home for pprof program. But do note that
|
||||
original pprof (which is still included with gperftools) is now
|
||||
deprecated in favor of golang version at https://github.com/google/pprof
|
||||
|
||||
|
||||
TCMALLOC
|
||||
--------
|
||||
Just link in -ltcmalloc or -ltcmalloc_minimal to get the advantages of
|
||||
tcmalloc -- a replacement for malloc and new. See below for some
|
||||
environment variables you can use with tcmalloc, as well.
|
||||
|
||||
tcmalloc functionality is available on all systems we've tested; see
|
||||
INSTALL for more details. See README_windows.txt for instructions on
|
||||
using tcmalloc on Windows.
|
||||
|
||||
when compiling. gcc makes some optimizations assuming it is using its
|
||||
own, built-in malloc; that assumption obviously isn't true with
|
||||
tcmalloc. In practice, we haven't seen any problems with this, but
|
||||
the expected risk is highest for users who register their own malloc
|
||||
hooks with tcmalloc (using gperftools/malloc_hook.h). The risk is
|
||||
lowest for folks who use tcmalloc_minimal (or, of course, who pass in
|
||||
the above flags :-) ).
|
||||
|
||||
|
||||
HEAP PROFILER
|
||||
-------------
|
||||
See docs/heapprofile.html for information about how to use tcmalloc's
|
||||
heap profiler and analyze its output.
|
||||
|
||||
As a quick-start, do the following after installing this package:
|
||||
|
||||
1) Link your executable with -ltcmalloc
|
||||
2) Run your executable with the HEAPPROFILE environment var set:
|
||||
$ HEAPPROFILE=/tmp/heapprof <path/to/binary> [binary args]
|
||||
3) Run pprof to analyze the heap usage
|
||||
$ pprof <path/to/binary> /tmp/heapprof.0045.heap # run 'ls' to see options
|
||||
$ pprof --gv <path/to/binary> /tmp/heapprof.0045.heap
|
||||
|
||||
You can also use LD_PRELOAD to heap-profile an executable that you
|
||||
didn't compile.
|
||||
|
||||
There are other environment variables, besides HEAPPROFILE, you can
|
||||
set to adjust the heap-profiler behavior; c.f. "ENVIRONMENT VARIABLES"
|
||||
below.
|
||||
|
||||
The heap profiler is available on all unix-based systems we've tested;
|
||||
see INSTALL for more details. It is not currently available on Windows.
|
||||
|
||||
|
||||
HEAP CHECKER
|
||||
------------
|
||||
See docs/heap_checker.html for information about how to use tcmalloc's
|
||||
heap checker.
|
||||
|
||||
In order to catch all heap leaks, tcmalloc must be linked *last* into
|
||||
your executable. The heap checker may mischaracterize some memory
|
||||
accesses in libraries listed after it on the link line. For instance,
|
||||
it may report these libraries as leaking memory when they're not.
|
||||
(See the source code for more details.)
|
||||
|
||||
Here's a quick-start for how to use:
|
||||
|
||||
As a quick-start, do the following after installing this package:
|
||||
|
||||
1) Link your executable with -ltcmalloc
|
||||
2) Run your executable with the HEAPCHECK environment var set:
|
||||
$ HEAPCHECK=1 <path/to/binary> [binary args]
|
||||
|
||||
Other values for HEAPCHECK: normal (equivalent to "1"), strict, draconian
|
||||
|
||||
You can also use LD_PRELOAD to heap-check an executable that you
|
||||
didn't compile.
|
||||
|
||||
The heap checker is only available on Linux at this time; see INSTALL
|
||||
for more details.
|
||||
|
||||
|
||||
CPU PROFILER
|
||||
------------
|
||||
See docs/cpuprofile.html for information about how to use the CPU
|
||||
profiler and analyze its output.
|
||||
|
||||
As a quick-start, do the following after installing this package:
|
||||
|
||||
1) Link your executable with -lprofiler
|
||||
2) Run your executable with the CPUPROFILE environment var set:
|
||||
$ CPUPROFILE=/tmp/prof.out <path/to/binary> [binary args]
|
||||
3) Run pprof to analyze the CPU usage
|
||||
$ pprof <path/to/binary> /tmp/prof.out # -pg-like text output
|
||||
$ pprof --gv <path/to/binary> /tmp/prof.out # really cool graphical output
|
||||
|
||||
There are other environment variables, besides CPUPROFILE, you can set
|
||||
to adjust the cpu-profiler behavior; cf "ENVIRONMENT VARIABLES" below.
|
||||
|
||||
The CPU profiler is available on all unix-based systems we've tested;
|
||||
see INSTALL for more details. It is not currently available on Windows.
|
||||
|
||||
NOTE: CPU profiling doesn't work after fork (unless you immediately
|
||||
do an exec()-like call afterwards). Furthermore, if you do
|
||||
fork, and the child calls exit(), it may corrupt the profile
|
||||
data. You can use _exit() to work around this. We hope to have
|
||||
a fix for both problems in the next release of perftools
|
||||
(hopefully perftools 1.2).
|
||||
|
||||
|
||||
EVERYTHING IN ONE
|
||||
-----------------
|
||||
If you want the CPU profiler, heap profiler, and heap leak-checker to
|
||||
all be available for your application, you can do:
|
||||
gcc -o myapp ... -lprofiler -ltcmalloc
|
||||
|
||||
However, if you have a reason to use the static versions of the
|
||||
library, this two-library linking won't work:
|
||||
gcc -o myapp ... /usr/lib/libprofiler.a /usr/lib/libtcmalloc.a # errors!
|
||||
|
||||
Instead, use the special libtcmalloc_and_profiler library, which we
|
||||
make for just this purpose:
|
||||
gcc -o myapp ... /usr/lib/libtcmalloc_and_profiler.a
|
||||
|
||||
|
||||
CONFIGURATION OPTIONS
|
||||
---------------------
|
||||
For advanced users, there are several flags you can pass to
|
||||
'./configure' that tweak tcmalloc performance. (These are in addition
|
||||
to the environment variables you can set at runtime to affect
|
||||
tcmalloc, described below.) See the INSTALL file for details.
|
||||
|
||||
|
||||
ENVIRONMENT VARIABLES
|
||||
---------------------
|
||||
The cpu profiler, heap checker, and heap profiler will lie dormant,
|
||||
using no memory or CPU, until you turn them on. (Thus, there's no
|
||||
harm in linking -lprofiler into every application, and also -ltcmalloc
|
||||
assuming you're ok using the non-libc malloc library.)
|
||||
|
||||
The easiest way to turn them on is by setting the appropriate
|
||||
environment variables. We have several variables that let you
|
||||
enable/disable features as well as tweak parameters.
|
||||
|
||||
Here are some of the most important variables:
|
||||
|
||||
HEAPPROFILE=<pre> -- turns on heap profiling and dumps data using this prefix
|
||||
HEAPCHECK=<type> -- turns on heap checking with strictness 'type'
|
||||
CPUPROFILE=<file> -- turns on cpu profiling and dumps data to this file.
|
||||
PROFILESELECTED=1 -- if set, cpu-profiler will only profile regions of code
|
||||
surrounded with ProfilerEnable()/ProfilerDisable().
|
||||
CPUPROFILE_FREQUENCY=x-- how many interrupts/second the cpu-profiler samples.
|
||||
|
||||
PERFTOOLS_VERBOSE=<level> -- the higher level, the more messages malloc emits
|
||||
MALLOCSTATS=<level> -- prints memory-use stats at program-exit
|
||||
|
||||
For a full list of variables, see the documentation pages:
|
||||
docs/cpuprofile.html
|
||||
docs/heapprofile.html
|
||||
docs/heap_checker.html
|
||||
|
||||
|
||||
COMPILING ON NON-LINUX SYSTEMS
|
||||
------------------------------
|
||||
|
||||
Perftools was developed and tested on x86 Linux systems, and it works
|
||||
in its full generality only on those systems. However, we've
|
||||
successfully ported much of the tcmalloc library to FreeBSD, Solaris
|
||||
x86, and Darwin (Mac OS X) x86 and ppc; and we've ported the basic
|
||||
functionality in tcmalloc_minimal to Windows. See INSTALL for details.
|
||||
See README_windows.txt for details on the Windows port.
|
||||
|
||||
|
||||
PERFORMANCE
|
||||
-----------
|
||||
|
||||
If you're interested in some third-party comparisons of tcmalloc to
|
||||
other malloc libraries, here are a few web pages that have been
|
||||
brought to our attention. The first discusses the effect of using
|
||||
various malloc libraries on OpenLDAP. The second compares tcmalloc to
|
||||
win32's malloc.
|
||||
http://www.highlandsun.com/hyc/malloc/
|
||||
http://gaiacrtn.free.fr/articles/win32perftools.html
|
||||
|
||||
It's possible to build tcmalloc in a way that trades off faster
|
||||
performance (particularly for deletes) at the cost of more memory
|
||||
fragmentation (that is, more unusable memory on your system). See the
|
||||
INSTALL file for details.
|
||||
|
||||
|
||||
OLD SYSTEM ISSUES
|
||||
-----------------
|
||||
|
||||
When compiling perftools on some old systems, like RedHat 8, you may
|
||||
get an error like this:
|
||||
___tls_get_addr: symbol not found
|
||||
|
||||
This means that you have a system where some parts are updated enough
|
||||
to support Thread Local Storage, but others are not. The perftools
|
||||
configure script can't always detect this kind of case, leading to
|
||||
that error. To fix it, just comment out (or delete) the line
|
||||
#define HAVE_TLS 1
|
||||
in your config.h file before building.
|
||||
|
||||
|
||||
64-BIT ISSUES
|
||||
-------------
|
||||
|
||||
There are two issues that can cause program hangs or crashes on x86_64
|
||||
64-bit systems, which use the libunwind library to get stack-traces.
|
||||
Neither issue should affect the core tcmalloc library; they both
|
||||
affect the perftools tools such as cpu-profiler, heap-checker, and
|
||||
heap-profiler.
|
||||
|
||||
1) Some libc's -- at least glibc 2.4 on x86_64 -- have a bug where the
|
||||
libc function dl_iterate_phdr() acquires its locks in the wrong
|
||||
order. This bug should not affect tcmalloc, but may cause occasional
|
||||
deadlock with the cpu-profiler, heap-profiler, and heap-checker.
|
||||
Its likeliness increases the more dlopen() commands an executable has.
|
||||
Most executables don't have any, though several library routines like
|
||||
getgrgid() call dlopen() behind the scenes.
|
||||
|
||||
2) On x86-64 64-bit systems, while tcmalloc itself works fine, the
|
||||
cpu-profiler tool is unreliable: it will sometimes work, but sometimes
|
||||
cause a segfault. I'll explain the problem first, and then some
|
||||
workarounds.
|
||||
|
||||
Note that this only affects the cpu-profiler, which is a
|
||||
gperftools feature you must turn on manually by setting the
|
||||
CPUPROFILE environment variable. If you do not turn on cpu-profiling,
|
||||
you shouldn't see any crashes due to perftools.
|
||||
|
||||
The gory details: The underlying problem is in the backtrace()
|
||||
function, which is a built-in function in libc.
|
||||
Backtracing is fairly straightforward in the normal case, but can run
|
||||
into problems when having to backtrace across a signal frame.
|
||||
Unfortunately, the cpu-profiler uses signals in order to register a
|
||||
profiling event, so every backtrace that the profiler does crosses a
|
||||
signal frame.
|
||||
|
||||
In our experience, the only time there is trouble is when the signal
|
||||
fires in the middle of pthread_mutex_lock. pthread_mutex_lock is
|
||||
called quite a bit from system libraries, particularly at program
|
||||
startup and when creating a new thread.
|
||||
|
||||
The solution: The dwarf debugging format has support for 'cfi
|
||||
annotations', which make it easy to recognize a signal frame. Some OS
|
||||
distributions, such as Fedora and gentoo 2007.0, already have added
|
||||
cfi annotations to their libc. A future version of libunwind should
|
||||
recognize these annotations; these systems should not see any
|
||||
crashes.
|
||||
|
||||
Workarounds: If you see problems with crashes when running the
|
||||
cpu-profiler, consider inserting ProfilerStart()/ProfilerStop() into
|
||||
your code, rather than setting CPUPROFILE. This will profile only
|
||||
those sections of the codebase. Though we haven't done much testing,
|
||||
in theory this should reduce the chance of crashes by limiting the
|
||||
signal generation to only a small part of the codebase. Ideally, you
|
||||
would not use ProfilerStart()/ProfilerStop() around code that spawns
|
||||
new threads, or is otherwise likely to cause a call to
|
||||
pthread_mutex_lock!
|
||||
|
||||
---
|
||||
17 May 2011
|
120
trunk/3rdparty/gperftools-2-fit/README_windows.txt
vendored
Normal file
|
@ -0,0 +1,120 @@
|
|||
--- COMPILING
|
||||
|
||||
This project has begun being ported to Windows, only tcmalloc_minimal
|
||||
is supported at this time. A working solution file exists in this
|
||||
directory:
|
||||
gperftools.sln
|
||||
|
||||
You can load this solution file into VC++ 7.1 (Visual Studio 2003) or
|
||||
later -- in the latter case, it will automatically convert the files
|
||||
to the latest format for you.
|
||||
|
||||
When you build the solution, it will create a number of unittests,
|
||||
which you can run by hand (or, more easily, under the Visual Studio
|
||||
debugger) to make sure everything is working properly on your system.
|
||||
The binaries will end up in a directory called "debug" or "release" in
|
||||
the top-level directory (next to the .sln file). It will also create
|
||||
two binaries, nm-pdb and addr2line-pdb, which you should install in
|
||||
the same directory you install the 'pprof' perl script.
|
||||
|
||||
I don't know very much about how to install DLLs on Windows, so you'll
|
||||
have to figure out that part for yourself. If you choose to just
|
||||
re-use the existing .sln, make sure you set the IncludeDir's
|
||||
appropriately! Look at the properties for libtcmalloc_minimal.dll.
|
||||
|
||||
Note that these systems are set to build in Debug mode by default.
|
||||
You may want to change them to Release mode.
|
||||
|
||||
To use tcmalloc_minimal in your own projects, you should only need to
|
||||
build the dll and install it someplace, so you can link it into
|
||||
further binaries. To use the dll, you need to add the following to
|
||||
the linker line of your executable:
|
||||
"libtcmalloc_minimal.lib" /INCLUDE:"__tcmalloc"
|
||||
|
||||
Here is how to accomplish this in Visual Studio 2005 (VC8):
|
||||
|
||||
1) Have your executable depend on the tcmalloc library by selecting
|
||||
"Project Dependencies..." from the "Project" menu. Your executable
|
||||
should depend on "libtcmalloc_minimal".
|
||||
|
||||
2) Have your executable depend on a tcmalloc symbol -- this is
|
||||
necessary so the linker doesn't "optimize out" the libtcmalloc
|
||||
dependency -- by right-clicking on your executable's project (in
|
||||
the solution explorer), selecting Properties from the pull-down
|
||||
menu, then selecting "Configuration Properties" -> "Linker" ->
|
||||
"Input". Then, in the "Force Symbol References" field, enter the
|
||||
text "__tcmalloc" (without the quotes). Be sure to do this for both
|
||||
debug and release modes!
|
||||
|
||||
You can also link tcmalloc code in statically -- see the example
|
||||
project tcmalloc_minimal_unittest-static, which does this. For this
|
||||
to work, you'll need to add "/D PERFTOOLS_DLL_DECL=" to the compile
|
||||
line of every perftools .cc file. You do not need to depend on the
|
||||
tcmalloc symbol in this case (that is, you don't need to do either
|
||||
step 1 or step 2 from above).
|
||||
|
||||
An alternative to all the above is to statically link your application
|
||||
with libc, and then replace its malloc with tcmalloc. This allows you
|
||||
to just build and link your program normally; the tcmalloc support
|
||||
comes in a post-processing step. This is more reliable than the above
|
||||
technique (which depends on run-time patching, which is inherently
|
||||
fragile), though more work to set up. For details, see
|
||||
https://groups.google.com/group/google-perftools/browse_thread/thread/41cd3710af85e57b
|
||||
|
||||
|
||||
--- THE HEAP-PROFILER
|
||||
|
||||
The heap-profiler has had a preliminary port to Windows but does not
|
||||
build on Windows by default. It has not been well tested, and
|
||||
probably does not work at all when Frame Pointer Optimization (FPO) is
|
||||
enabled -- that is, in release mode. The other features of perftools,
|
||||
such as the cpu-profiler and leak-checker, have not yet been ported to
|
||||
Windows at all.
|
||||
|
||||
|
||||
--- WIN64
|
||||
|
||||
The function-patcher has to disassemble code, and is very
|
||||
x86-specific. However, the rest of perftools should work fine for
|
||||
both x86 and x64. In particular, if you use the 'statically link with
|
||||
libc, and replace its malloc with tcmalloc' approach, mentioned above,
|
||||
it should be possible to use tcmalloc with 64-bit windows.
|
||||
|
||||
As of perftools 1.10, there is some support for disassembling x86_64
|
||||
instructions, for work with win64. This work is preliminary, but the
|
||||
test file preamble_patcher_test.cc is provided to play around with
|
||||
that a bit. preamble_patcher_test will not compile on win32.
|
||||
|
||||
|
||||
--- ISSUES
|
||||
|
||||
NOTE FOR WIN2K USERS: According to reports
|
||||
(http://code.google.com/p/gperftools/issues/detail?id=127)
|
||||
the stack-tracing necessary for the heap-profiler does not work on
|
||||
Win2K. The best workaround is, if you are building on a Win2k system
|
||||
is to add "/D NO_TCMALLOC_SAMPLES=" to your build, to turn off the
|
||||
stack-tracing. You will not be able to use the heap-profiler if you
|
||||
do this.
|
||||
|
||||
NOTE ON _MSIZE and _RECALLOC: The tcmalloc version of _msize returns
|
||||
the size of the region tcmalloc allocated for you -- which is at least
|
||||
as many bytes you asked for, but may be more. (btw, these *are* bytes
|
||||
you own, even if you didn't ask for all of them, so it's correct code
|
||||
to access all of them if you want.) Unfortunately, the Windows CRT
|
||||
_recalloc() routine assumes that _msize returns exactly as many bytes
|
||||
as were requested. As a result, _recalloc() may not zero out new
|
||||
bytes correctly. IT'S SAFEST NOT TO USE _RECALLOC WITH TCMALLOC.
|
||||
_recalloc() is a tricky routine to use in any case (it's not safe to
|
||||
use with realloc, for instance).
|
||||
|
||||
|
||||
I have little experience with Windows programming, so there may be
|
||||
better ways to set this up than I've done! If you run across any
|
||||
problems, please post to the google-perftools Google Group, or report
|
||||
them on the gperftools Google Code site:
|
||||
http://groups.google.com/group/google-perftools
|
||||
http://code.google.com/p/gperftools/issues/list
|
||||
|
||||
-- craig
|
||||
|
||||
Last modified: 2 February 2012
|
47
trunk/3rdparty/gperftools-2-fit/TODO
vendored
Normal file
|
@ -0,0 +1,47 @@
|
|||
HEAP PROFILER
|
||||
|
||||
1) Fix heap profiling under all STLs
|
||||
* Find out how to force non-glibc STL libraries to call new() and
|
||||
delete() for every allocation / deallocation.
|
||||
* Make heap profiler ignore STL-internal allocations for those
|
||||
libraries under which we cannot profile accurately, so we only
|
||||
see object-level leaks.
|
||||
2) Remove dependency on tcmalloc?
|
||||
3) Port to non-linux O/Ses (right now code uses /proc for library info)
|
||||
4) Port to non-x86 architectures (locking code in spinlock is x86-specific)
|
||||
5) Port to C?
|
||||
6) Figure out how to get setenv() to work properly before main() in
|
||||
shared libaries, and get rid of the profile-naming hack once we
|
||||
do. (See HeapProfiler::Init().)
|
||||
|
||||
|
||||
HEAP CHECKER
|
||||
|
||||
1) Remove requirement that the heap-checker must be linked last into
|
||||
an application (hard! -- it needs its global constructor to run
|
||||
first)
|
||||
|
||||
TCMALLOC
|
||||
|
||||
1) Implement mallinfo/mallopt
|
||||
2) Have tcmalloc work correctly when libpthread is not linked in
|
||||
(currently working for glibc, could use other libc's too)
|
||||
3) Return memory to the system when requirements drop
|
||||
4) Explore coloring allocated objects to avoid cache conflicts
|
||||
5) Explore biasing reclamation to larger addresses
|
||||
6) Add contention stats to a synchronization.cc (can do spinlocks,
|
||||
but threads? -- may have to provide our own thread implementation)
|
||||
|
||||
CPU PROFILER
|
||||
|
||||
1) Figure out how to get setenv() to work properly before main() in
|
||||
shared libaries(), and get rid of the profile-naming hack once we
|
||||
do. (See Profiler::GetUniquePathFromEnv().)
|
||||
2) Resolve crashing problems on x86_64 (see README)
|
||||
|
||||
STACKTRACE
|
||||
|
||||
1) Remove dependency on linux/x86
|
||||
|
||||
---
|
||||
11 March 2008
|
1181
trunk/3rdparty/gperftools-2-fit/aclocal.m4
vendored
Normal file
108
trunk/3rdparty/gperftools-2-fit/benchmark/binary_trees.cc
vendored
Normal file
|
@ -0,0 +1,108 @@
|
|||
// -*- Mode: C++; c-basic-offset: 2; indent-tabs-mode: nil -*-
|
||||
//
|
||||
// Copied from
|
||||
// http://benchmarksgame.alioth.debian.org/u64q/program.php?test=binarytrees&lang=gpp&id=2
|
||||
// and slightly modified (particularly by adding multi-threaded
|
||||
// operation to hit malloc harder).
|
||||
//
|
||||
// This version of binary trees is mostly new/delete benchmark
|
||||
//
|
||||
// NOTE: copyright of this code is unclear, but we only distribute
|
||||
// source.
|
||||
|
||||
/* The Computer Language Benchmarks Game
|
||||
* http://benchmarksgame.alioth.debian.org/
|
||||
*
|
||||
* Contributed by Jon Harrop
|
||||
* Modified by Alex Mizrahi
|
||||
* Adapted for gperftools and added threads by Aliaksei Kandratsenka
|
||||
*/
|
||||
|
||||
#include <algorithm>
|
||||
#include <errno.h>
|
||||
#include <iostream>
|
||||
#include <pthread.h>
|
||||
#include <stdint.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <vector>
|
||||
|
||||
struct Node {
|
||||
Node *l, *r;
|
||||
int i;
|
||||
Node(int i2) : l(0), r(0), i(i2) {}
|
||||
Node(Node *l2, int i2, Node *r2) : l(l2), r(r2), i(i2) {}
|
||||
~Node() { delete l; delete r; }
|
||||
int check() const {
|
||||
if (l) {
|
||||
return l->check() + i - r->check();
|
||||
} else {
|
||||
return i;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
Node *make(int i, int d) {
|
||||
if (d == 0) return new Node(i);
|
||||
return new Node(make(2*i-1, d-1), i, make(2*i, d-1));
|
||||
}
|
||||
|
||||
void run(int given_depth) {
|
||||
int min_depth = 4,
|
||||
max_depth = std::max(min_depth+2,
|
||||
given_depth),
|
||||
stretch_depth = max_depth+1;
|
||||
|
||||
{
|
||||
Node *c = make(0, stretch_depth);
|
||||
std::cout << "stretch tree of depth " << stretch_depth << "\t "
|
||||
<< "check: " << c->check() << std::endl;
|
||||
delete c;
|
||||
}
|
||||
|
||||
Node *long_lived_tree=make(0, max_depth);
|
||||
|
||||
for (int d=min_depth; d<=max_depth; d+=2) {
|
||||
int iterations = 1 << (max_depth - d + min_depth), c=0;
|
||||
for (int i=1; i<=iterations; ++i) {
|
||||
Node *a = make(i, d), *b = make(-i, d);
|
||||
c += a->check() + b->check();
|
||||
delete a;
|
||||
delete b;
|
||||
}
|
||||
std::cout << (2*iterations) << "\t trees of depth " << d << "\t "
|
||||
<< "check: " << c << std::endl;
|
||||
}
|
||||
|
||||
std::cout << "long lived tree of depth " << max_depth << "\t "
|
||||
<< "check: " << (long_lived_tree->check()) << "\n";
|
||||
|
||||
delete long_lived_tree;
|
||||
}
|
||||
|
||||
static void *run_tramp(void *_a) {
|
||||
intptr_t a = reinterpret_cast<intptr_t>(_a);
|
||||
run(a);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int main(int argc, char *argv[]) {
|
||||
int given_depth = argc >= 2 ? atoi(argv[1]) : 20;
|
||||
int thread_count = std::max(1, argc >= 3 ? atoi(argv[2]) : 1) - 1;
|
||||
std::vector<pthread_t> threads(thread_count);
|
||||
|
||||
for (int i = 0; i < thread_count; i++) {
|
||||
int rv = pthread_create(&threads[i], NULL,
|
||||
run_tramp,
|
||||
reinterpret_cast<void *>(given_depth));
|
||||
if (rv) {
|
||||
errno = rv;
|
||||
perror("pthread_create");
|
||||
}
|
||||
}
|
||||
run_tramp(reinterpret_cast<void *>(given_depth));
|
||||
for (int i = 0; i < thread_count; i++) {
|
||||
pthread_join(threads[i], NULL);
|
||||
}
|
||||
return 0;
|
||||
}
|
293
trunk/3rdparty/gperftools-2-fit/benchmark/malloc_bench.cc
vendored
Normal file
|
@ -0,0 +1,293 @@
|
|||
// -*- Mode: C++; c-basic-offset: 2; indent-tabs-mode: nil -*-
|
||||
// Redistribution and use in source and binary forms, with or without
|
||||
// modification, are permitted provided that the following conditions are
|
||||
// met:
|
||||
//
|
||||
// * Redistributions of source code must retain the above copyright
|
||||
// notice, this list of conditions and the following disclaimer.
|
||||
// * Redistributions in binary form must reproduce the above
|
||||
// copyright notice, this list of conditions and the following disclaimer
|
||||
// in the documentation and/or other materials provided with the
|
||||
// distribution.
|
||||
// * Neither the name of Google Inc. nor the names of its
|
||||
// contributors may be used to endorse or promote products derived from
|
||||
// this software without specific prior written permission.
|
||||
//
|
||||
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
||||
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||||
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
||||
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
|
||||
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
||||
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include <algorithm>
|
||||
|
||||
#include "run_benchmark.h"
|
||||
|
||||
static void bench_fastpath_throughput(long iterations,
|
||||
uintptr_t param)
|
||||
{
|
||||
size_t sz = 32;
|
||||
for (; iterations>0; iterations--) {
|
||||
void *p = malloc(sz);
|
||||
if (!p) {
|
||||
abort();
|
||||
}
|
||||
free(p);
|
||||
// this makes next iteration use different free list. So
|
||||
// subsequent iterations may actually overlap in time.
|
||||
sz = ((sz * 8191) & 511) + 16;
|
||||
}
|
||||
}
|
||||
|
||||
static void bench_fastpath_dependent(long iterations,
|
||||
uintptr_t param)
|
||||
{
|
||||
size_t sz = 32;
|
||||
for (; iterations>0; iterations--) {
|
||||
void *p = malloc(sz);
|
||||
if (!p) {
|
||||
abort();
|
||||
}
|
||||
free(p);
|
||||
// this makes next iteration depend on current iteration. But this
|
||||
// iteration's free may still overlap with next iteration's malloc
|
||||
sz = ((sz | reinterpret_cast<size_t>(p)) & 511) + 16;
|
||||
}
|
||||
}
|
||||
|
||||
static void bench_fastpath_simple(long iterations,
|
||||
uintptr_t param)
|
||||
{
|
||||
size_t sz = static_cast<size_t>(param);
|
||||
for (; iterations>0; iterations--) {
|
||||
void *p = malloc(sz);
|
||||
if (!p) {
|
||||
abort();
|
||||
}
|
||||
free(p);
|
||||
// next iteration will use same free list as this iteration. So it
|
||||
// should be prevent next iterations malloc to go too far before
|
||||
// free done. But using same size will make free "too fast" since
|
||||
// we'll hit size class cache.
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef __GNUC__
|
||||
#define HAVE_SIZED_FREE_OPTION
|
||||
|
||||
extern "C" void tc_free_sized(void *ptr, size_t size) __attribute__((weak));
|
||||
extern "C" void *tc_memalign(size_t align, size_t size) __attribute__((weak));
|
||||
|
||||
static bool is_sized_free_available(void)
|
||||
{
|
||||
return tc_free_sized != NULL;
|
||||
}
|
||||
|
||||
static bool is_memalign_available(void)
|
||||
{
|
||||
return tc_memalign != NULL;
|
||||
}
|
||||
|
||||
static void bench_fastpath_simple_sized(long iterations,
|
||||
uintptr_t param)
|
||||
{
|
||||
size_t sz = static_cast<size_t>(param);
|
||||
for (; iterations>0; iterations--) {
|
||||
void *p = malloc(sz);
|
||||
if (!p) {
|
||||
abort();
|
||||
}
|
||||
tc_free_sized(p, sz);
|
||||
// next iteration will use same free list as this iteration. So it
|
||||
// should be prevent next iterations malloc to go too far before
|
||||
// free done. But using same size will make free "too fast" since
|
||||
// we'll hit size class cache.
|
||||
}
|
||||
}
|
||||
|
||||
static void bench_fastpath_memalign(long iterations,
|
||||
uintptr_t param)
|
||||
{
|
||||
size_t sz = static_cast<size_t>(param);
|
||||
for (; iterations>0; iterations--) {
|
||||
void *p = tc_memalign(32, sz);
|
||||
if (!p) {
|
||||
abort();
|
||||
}
|
||||
free(p);
|
||||
// next iteration will use same free list as this iteration. So it
|
||||
// should be prevent next iterations malloc to go too far before
|
||||
// free done. But using same size will make free "too fast" since
|
||||
// we'll hit size class cache.
|
||||
}
|
||||
}
|
||||
|
||||
#endif // __GNUC__
|
||||
|
||||
#define STACKSZ (1 << 16)
|
||||
|
||||
static void bench_fastpath_stack(long iterations,
|
||||
uintptr_t _param)
|
||||
{
|
||||
|
||||
void *stack[STACKSZ];
|
||||
size_t sz = 64;
|
||||
long param = static_cast<long>(_param);
|
||||
param &= STACKSZ - 1;
|
||||
param = param ? param : 1;
|
||||
for (; iterations>0; iterations -= param) {
|
||||
for (long k = param-1; k >= 0; k--) {
|
||||
void *p = malloc(sz);
|
||||
if (!p) {
|
||||
abort();
|
||||
}
|
||||
stack[k] = p;
|
||||
// this makes next iteration depend on result of this iteration
|
||||
sz = ((sz | reinterpret_cast<size_t>(p)) & 511) + 16;
|
||||
}
|
||||
for (long k = 0; k < param; k++) {
|
||||
free(stack[k]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void bench_fastpath_stack_simple(long iterations,
|
||||
uintptr_t _param)
|
||||
{
|
||||
|
||||
void *stack[STACKSZ];
|
||||
size_t sz = 128;
|
||||
long param = static_cast<long>(_param);
|
||||
param &= STACKSZ - 1;
|
||||
param = param ? param : 1;
|
||||
for (; iterations>0; iterations -= param) {
|
||||
for (long k = param-1; k >= 0; k--) {
|
||||
void *p = malloc(sz);
|
||||
if (!p) {
|
||||
abort();
|
||||
}
|
||||
stack[k] = p;
|
||||
}
|
||||
for (long k = 0; k < param; k++) {
|
||||
free(stack[k]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void bench_fastpath_rnd_dependent(long iterations,
|
||||
uintptr_t _param)
|
||||
{
|
||||
static const uintptr_t rnd_c = 1013904223;
|
||||
static const uintptr_t rnd_a = 1664525;
|
||||
|
||||
void *ptrs[STACKSZ];
|
||||
size_t sz = 128;
|
||||
if ((_param & (_param - 1))) {
|
||||
abort();
|
||||
}
|
||||
if (_param > STACKSZ) {
|
||||
abort();
|
||||
}
|
||||
int param = static_cast<int>(_param);
|
||||
|
||||
for (; iterations>0; iterations -= param) {
|
||||
for (int k = param-1; k >= 0; k--) {
|
||||
void *p = malloc(sz);
|
||||
if (!p) {
|
||||
abort();
|
||||
}
|
||||
ptrs[k] = p;
|
||||
sz = ((sz | reinterpret_cast<size_t>(p)) & 511) + 16;
|
||||
}
|
||||
|
||||
// this will iterate through all objects in order that is
|
||||
// unpredictable to processor's prefetchers
|
||||
uint32_t rnd = 0;
|
||||
uint32_t free_idx = 0;
|
||||
do {
|
||||
free(ptrs[free_idx]);
|
||||
rnd = rnd * rnd_a + rnd_c;
|
||||
free_idx = rnd & (param - 1);
|
||||
} while (free_idx != 0);
|
||||
}
|
||||
}
|
||||
|
||||
static void *randomize_buffer[13<<20];
|
||||
|
||||
|
||||
void randomize_one_size_class(size_t size) {
|
||||
int count = (100<<20) / size;
|
||||
if (count * sizeof(randomize_buffer[0]) > sizeof(randomize_buffer)) {
|
||||
abort();
|
||||
}
|
||||
for (int i = 0; i < count; i++) {
|
||||
randomize_buffer[i] = malloc(size);
|
||||
}
|
||||
std::random_shuffle(randomize_buffer, randomize_buffer + count);
|
||||
for (int i = 0; i < count; i++) {
|
||||
free(randomize_buffer[i]);
|
||||
}
|
||||
}
|
||||
|
||||
void randomize_size_classes() {
|
||||
randomize_one_size_class(8);
|
||||
int i;
|
||||
for (i = 16; i < 256; i += 16) {
|
||||
randomize_one_size_class(i);
|
||||
}
|
||||
for (; i < 512; i += 32) {
|
||||
randomize_one_size_class(i);
|
||||
}
|
||||
for (; i < 1024; i += 64) {
|
||||
randomize_one_size_class(i);
|
||||
}
|
||||
for (; i < (4 << 10); i += 128) {
|
||||
randomize_one_size_class(i);
|
||||
}
|
||||
for (; i < (32 << 10); i += 1024) {
|
||||
randomize_one_size_class(i);
|
||||
}
|
||||
}
|
||||
|
||||
int main(void)
|
||||
{
|
||||
randomize_size_classes();
|
||||
|
||||
report_benchmark("bench_fastpath_throughput", bench_fastpath_throughput, 0);
|
||||
report_benchmark("bench_fastpath_dependent", bench_fastpath_dependent, 0);
|
||||
report_benchmark("bench_fastpath_simple", bench_fastpath_simple, 64);
|
||||
report_benchmark("bench_fastpath_simple", bench_fastpath_simple, 2048);
|
||||
report_benchmark("bench_fastpath_simple", bench_fastpath_simple, 16384);
|
||||
|
||||
#ifdef HAVE_SIZED_FREE_OPTION
|
||||
if (is_sized_free_available()) {
|
||||
report_benchmark("bench_fastpath_simple_sized", bench_fastpath_simple_sized, 64);
|
||||
report_benchmark("bench_fastpath_simple_sized", bench_fastpath_simple_sized, 2048);
|
||||
}
|
||||
|
||||
if (is_memalign_available()) {
|
||||
report_benchmark("bench_fastpath_memalign", bench_fastpath_memalign, 64);
|
||||
report_benchmark("bench_fastpath_memalign", bench_fastpath_memalign, 2048);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
for (int i = 8; i <= 512; i <<= 1) {
|
||||
report_benchmark("bench_fastpath_stack", bench_fastpath_stack, i);
|
||||
}
|
||||
report_benchmark("bench_fastpath_stack_simple", bench_fastpath_stack_simple, 32);
|
||||
report_benchmark("bench_fastpath_stack_simple", bench_fastpath_stack_simple, 8192);
|
||||
report_benchmark("bench_fastpath_rnd_dependent", bench_fastpath_rnd_dependent, 32);
|
||||
report_benchmark("bench_fastpath_rnd_dependent", bench_fastpath_rnd_dependent, 8192);
|
||||
return 0;
|
||||
}
|
112
trunk/3rdparty/gperftools-2-fit/benchmark/run_benchmark.c
vendored
Normal file
|
@ -0,0 +1,112 @@
|
|||
// -*- Mode: C; c-basic-offset: 2; indent-tabs-mode: nil -*-
|
||||
// Redistribution and use in source and binary forms, with or without
|
||||
// modification, are permitted provided that the following conditions are
|
||||
// met:
|
||||
//
|
||||
// * Redistributions of source code must retain the above copyright
|
||||
// notice, this list of conditions and the following disclaimer.
|
||||
// * Redistributions in binary form must reproduce the above
|
||||
// copyright notice, this list of conditions and the following disclaimer
|
||||
// in the documentation and/or other materials provided with the
|
||||
// distribution.
|
||||
// * Neither the name of Google Inc. nor the names of its
|
||||
// contributors may be used to endorse or promote products derived from
|
||||
// this software without specific prior written permission.
|
||||
//
|
||||
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
||||
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||||
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
||||
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
|
||||
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
||||
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
#include "run_benchmark.h"
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <sys/time.h>
|
||||
|
||||
struct internal_bench {
|
||||
bench_body body;
|
||||
uintptr_t param;
|
||||
};
|
||||
|
||||
static void run_body(struct internal_bench *b, long iterations)
|
||||
{
|
||||
b->body(iterations, b->param);
|
||||
}
|
||||
|
||||
static double measure_once(struct internal_bench *b, long iterations)
|
||||
{
|
||||
struct timeval tv_before, tv_after;
|
||||
int rv;
|
||||
double time;
|
||||
|
||||
rv = gettimeofday(&tv_before, NULL);
|
||||
if (rv) {
|
||||
perror("gettimeofday");
|
||||
abort();
|
||||
}
|
||||
|
||||
run_body(b, iterations);
|
||||
|
||||
rv = gettimeofday(&tv_after, NULL);
|
||||
if (rv) {
|
||||
perror("gettimeofday");
|
||||
abort();
|
||||
}
|
||||
tv_after.tv_sec -= tv_before.tv_sec;
|
||||
time = tv_after.tv_sec * 1E6 + tv_after.tv_usec;
|
||||
time -= tv_before.tv_usec;
|
||||
time *= 1000;
|
||||
return time;
|
||||
}
|
||||
|
||||
#define TRIAL_NSEC 0.3E9
|
||||
#define TARGET_NSEC 3E9
|
||||
|
||||
static double run_benchmark(struct internal_bench *b)
|
||||
{
|
||||
long iterations = 128;
|
||||
double nsec;
|
||||
while (1) {
|
||||
nsec = measure_once(b, iterations);
|
||||
if (nsec > TRIAL_NSEC) {
|
||||
break;
|
||||
}
|
||||
iterations <<= 1;
|
||||
}
|
||||
while (nsec < TARGET_NSEC) {
|
||||
iterations = (long)(iterations * TARGET_NSEC * 1.1 / nsec);
|
||||
nsec = measure_once(b, iterations);
|
||||
}
|
||||
return nsec / iterations;
|
||||
}
|
||||
|
||||
void report_benchmark(const char *name, bench_body body, uintptr_t param)
|
||||
{
|
||||
int i;
|
||||
struct internal_bench b = {.body = body, .param = param};
|
||||
for (i = 0; i < 3; i++) {
|
||||
double nsec = run_benchmark(&b);
|
||||
int slen;
|
||||
int padding_size;
|
||||
|
||||
slen = printf("Benchmark: %s", name);
|
||||
if (param && name[strlen(name)-1] != ')') {
|
||||
slen += printf("(%lld)", (long long)param);
|
||||
}
|
||||
padding_size = 60 - slen;
|
||||
if (padding_size < 1) {
|
||||
padding_size = 1;
|
||||
}
|
||||
printf("%*c%f nsec\n", padding_size, ' ', nsec);
|
||||
fflush(stdout);
|
||||
}
|
||||
}
|
43
trunk/3rdparty/gperftools-2-fit/benchmark/run_benchmark.h
vendored
Normal file
|
@ -0,0 +1,43 @@
|
|||
// -*- Mode: C; c-basic-offset: 2; indent-tabs-mode: nil -*-
|
||||
// Redistribution and use in source and binary forms, with or without
|
||||
// modification, are permitted provided that the following conditions are
|
||||
// met:
|
||||
//
|
||||
// * Redistributions of source code must retain the above copyright
|
||||
// notice, this list of conditions and the following disclaimer.
|
||||
// * Redistributions in binary form must reproduce the above
|
||||
// copyright notice, this list of conditions and the following disclaimer
|
||||
// in the documentation and/or other materials provided with the
|
||||
// distribution.
|
||||
// * Neither the name of Google Inc. nor the names of its
|
||||
// contributors may be used to endorse or promote products derived from
|
||||
// this software without specific prior written permission.
|
||||
//
|
||||
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
||||
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||||
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
||||
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
|
||||
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
||||
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
#ifndef _RUN_BENCHMARK_H_
|
||||
#define _RUN_BENCHMARK_H_
|
||||
#include <stdint.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
typedef void (*bench_body)(long iterations, uintptr_t param);
|
||||
|
||||
void report_benchmark(const char *name, bench_body body, uintptr_t param);
|
||||
|
||||
#ifdef __cplusplus
|
||||
} // extern "C"
|
||||
#endif
|
||||
|
||||
#endif // _RUN_BENCHMARK_H_
|
348
trunk/3rdparty/gperftools-2-fit/compile
vendored
Executable file
|
@ -0,0 +1,348 @@
|
|||
#! /bin/sh
|
||||
# Wrapper for compilers which do not understand '-c -o'.
|
||||
|
||||
scriptversion=2018-03-07.03; # UTC
|
||||
|
||||
# Copyright (C) 1999-2020 Free Software Foundation, Inc.
|
||||
# Written by Tom Tromey <tromey@cygnus.com>.
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; either version 2, or (at your option)
|
||||
# any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
|
||||
# As a special exception to the GNU General Public License, if you
|
||||
# distribute this file as part of a program that contains a
|
||||
# configuration script generated by Autoconf, you may include it under
|
||||
# the same distribution terms that you use for the rest of that program.
|
||||
|
||||
# This file is maintained in Automake, please report
|
||||
# bugs to <bug-automake@gnu.org> or send patches to
|
||||
# <automake-patches@gnu.org>.
|
||||
|
||||
nl='
|
||||
'
|
||||
|
||||
# We need space, tab and new line, in precisely that order. Quoting is
|
||||
# there to prevent tools from complaining about whitespace usage.
|
||||
IFS=" "" $nl"
|
||||
|
||||
file_conv=
|
||||
|
||||
# func_file_conv build_file lazy
|
||||
# Convert a $build file to $host form and store it in $file
|
||||
# Currently only supports Windows hosts. If the determined conversion
|
||||
# type is listed in (the comma separated) LAZY, no conversion will
|
||||
# take place.
|
||||
func_file_conv ()
|
||||
{
|
||||
file=$1
|
||||
case $file in
|
||||
/ | /[!/]*) # absolute file, and not a UNC file
|
||||
if test -z "$file_conv"; then
|
||||
# lazily determine how to convert abs files
|
||||
case `uname -s` in
|
||||
MINGW*)
|
||||
file_conv=mingw
|
||||
;;
|
||||
CYGWIN* | MSYS*)
|
||||
file_conv=cygwin
|
||||
;;
|
||||
*)
|
||||
file_conv=wine
|
||||
;;
|
||||
esac
|
||||
fi
|
||||
case $file_conv/,$2, in
|
||||
*,$file_conv,*)
|
||||
;;
|
||||
mingw/*)
|
||||
file=`cmd //C echo "$file " | sed -e 's/"\(.*\) " *$/\1/'`
|
||||
;;
|
||||
cygwin/* | msys/*)
|
||||
file=`cygpath -m "$file" || echo "$file"`
|
||||
;;
|
||||
wine/*)
|
||||
file=`winepath -w "$file" || echo "$file"`
|
||||
;;
|
||||
esac
|
||||
;;
|
||||
esac
|
||||
}
|
||||
|
||||
# func_cl_dashL linkdir
|
||||
# Make cl look for libraries in LINKDIR
|
||||
func_cl_dashL ()
|
||||
{
|
||||
func_file_conv "$1"
|
||||
if test -z "$lib_path"; then
|
||||
lib_path=$file
|
||||
else
|
||||
lib_path="$lib_path;$file"
|
||||
fi
|
||||
linker_opts="$linker_opts -LIBPATH:$file"
|
||||
}
|
||||
|
||||
# func_cl_dashl library
|
||||
# Do a library search-path lookup for cl
|
||||
func_cl_dashl ()
|
||||
{
|
||||
lib=$1
|
||||
found=no
|
||||
save_IFS=$IFS
|
||||
IFS=';'
|
||||
for dir in $lib_path $LIB
|
||||
do
|
||||
IFS=$save_IFS
|
||||
if $shared && test -f "$dir/$lib.dll.lib"; then
|
||||
found=yes
|
||||
lib=$dir/$lib.dll.lib
|
||||
break
|
||||
fi
|
||||
if test -f "$dir/$lib.lib"; then
|
||||
found=yes
|
||||
lib=$dir/$lib.lib
|
||||
break
|
||||
fi
|
||||
if test -f "$dir/lib$lib.a"; then
|
||||
found=yes
|
||||
lib=$dir/lib$lib.a
|
||||
break
|
||||
fi
|
||||
done
|
||||
IFS=$save_IFS
|
||||
|
||||
if test "$found" != yes; then
|
||||
lib=$lib.lib
|
||||
fi
|
||||
}
|
||||
|
||||
# func_cl_wrapper cl arg...
|
||||
# Adjust compile command to suit cl
|
||||
func_cl_wrapper ()
|
||||
{
|
||||
# Assume a capable shell
|
||||
lib_path=
|
||||
shared=:
|
||||
linker_opts=
|
||||
for arg
|
||||
do
|
||||
if test -n "$eat"; then
|
||||
eat=
|
||||
else
|
||||
case $1 in
|
||||
-o)
|
||||
# configure might choose to run compile as 'compile cc -o foo foo.c'.
|
||||
eat=1
|
||||
case $2 in
|
||||
*.o | *.[oO][bB][jJ])
|
||||
func_file_conv "$2"
|
||||
set x "$@" -Fo"$file"
|
||||
shift
|
||||
;;
|
||||
*)
|
||||
func_file_conv "$2"
|
||||
set x "$@" -Fe"$file"
|
||||
shift
|
||||
;;
|
||||
esac
|
||||
;;
|
||||
-I)
|
||||
eat=1
|
||||
func_file_conv "$2" mingw
|
||||
set x "$@" -I"$file"
|
||||
shift
|
||||
;;
|
||||
-I*)
|
||||
func_file_conv "${1#-I}" mingw
|
||||
set x "$@" -I"$file"
|
||||
shift
|
||||
;;
|
||||
-l)
|
||||
eat=1
|
||||
func_cl_dashl "$2"
|
||||
set x "$@" "$lib"
|
||||
shift
|
||||
;;
|
||||
-l*)
|
||||
func_cl_dashl "${1#-l}"
|
||||
set x "$@" "$lib"
|
||||
shift
|
||||
;;
|
||||
-L)
|
||||
eat=1
|
||||
func_cl_dashL "$2"
|
||||
;;
|
||||
-L*)
|
||||
func_cl_dashL "${1#-L}"
|
||||
;;
|
||||
-static)
|
||||
shared=false
|
||||
;;
|
||||
-Wl,*)
|
||||
arg=${1#-Wl,}
|
||||
save_ifs="$IFS"; IFS=','
|
||||
for flag in $arg; do
|
||||
IFS="$save_ifs"
|
||||
linker_opts="$linker_opts $flag"
|
||||
done
|
||||
IFS="$save_ifs"
|
||||
;;
|
||||
-Xlinker)
|
||||
eat=1
|
||||
linker_opts="$linker_opts $2"
|
||||
;;
|
||||
-*)
|
||||
set x "$@" "$1"
|
||||
shift
|
||||
;;
|
||||
*.cc | *.CC | *.cxx | *.CXX | *.[cC]++)
|
||||
func_file_conv "$1"
|
||||
set x "$@" -Tp"$file"
|
||||
shift
|
||||
;;
|
||||
*.c | *.cpp | *.CPP | *.lib | *.LIB | *.Lib | *.OBJ | *.obj | *.[oO])
|
||||
func_file_conv "$1" mingw
|
||||
set x "$@" "$file"
|
||||
shift
|
||||
;;
|
||||
*)
|
||||
set x "$@" "$1"
|
||||
shift
|
||||
;;
|
||||
esac
|
||||
fi
|
||||
shift
|
||||
done
|
||||
if test -n "$linker_opts"; then
|
||||
linker_opts="-link$linker_opts"
|
||||
fi
|
||||
exec "$@" $linker_opts
|
||||
exit 1
|
||||
}
|
||||
|
||||
eat=
|
||||
|
||||
case $1 in
|
||||
'')
|
||||
echo "$0: No command. Try '$0 --help' for more information." 1>&2
|
||||
exit 1;
|
||||
;;
|
||||
-h | --h*)
|
||||
cat <<\EOF
|
||||
Usage: compile [--help] [--version] PROGRAM [ARGS]
|
||||
|
||||
Wrapper for compilers which do not understand '-c -o'.
|
||||
Remove '-o dest.o' from ARGS, run PROGRAM with the remaining
|
||||
arguments, and rename the output as expected.
|
||||
|
||||
If you are trying to build a whole package this is not the
|
||||
right script to run: please start by reading the file 'INSTALL'.
|
||||
|
||||
Report bugs to <bug-automake@gnu.org>.
|
||||
EOF
|
||||
exit $?
|
||||
;;
|
||||
-v | --v*)
|
||||
echo "compile $scriptversion"
|
||||
exit $?
|
||||
;;
|
||||
cl | *[/\\]cl | cl.exe | *[/\\]cl.exe | \
|
||||
icl | *[/\\]icl | icl.exe | *[/\\]icl.exe )
|
||||
func_cl_wrapper "$@" # Doesn't return...
|
||||
;;
|
||||
esac
|
||||
|
||||
ofile=
|
||||
cfile=
|
||||
|
||||
for arg
|
||||
do
|
||||
if test -n "$eat"; then
|
||||
eat=
|
||||
else
|
||||
case $1 in
|
||||
-o)
|
||||
# configure might choose to run compile as 'compile cc -o foo foo.c'.
|
||||
# So we strip '-o arg' only if arg is an object.
|
||||
eat=1
|
||||
case $2 in
|
||||
*.o | *.obj)
|
||||
ofile=$2
|
||||
;;
|
||||
*)
|
||||
set x "$@" -o "$2"
|
||||
shift
|
||||
;;
|
||||
esac
|
||||
;;
|
||||
*.c)
|
||||
cfile=$1
|
||||
set x "$@" "$1"
|
||||
shift
|
||||
;;
|
||||
*)
|
||||
set x "$@" "$1"
|
||||
shift
|
||||
;;
|
||||
esac
|
||||
fi
|
||||
shift
|
||||
done
|
||||
|
||||
if test -z "$ofile" || test -z "$cfile"; then
|
||||
# If no '-o' option was seen then we might have been invoked from a
|
||||
# pattern rule where we don't need one. That is ok -- this is a
|
||||
# normal compilation that the losing compiler can handle. If no
|
||||
# '.c' file was seen then we are probably linking. That is also
|
||||
# ok.
|
||||
exec "$@"
|
||||
fi
|
||||
|
||||
# Name of file we expect compiler to create.
|
||||
cofile=`echo "$cfile" | sed 's|^.*[\\/]||; s|^[a-zA-Z]:||; s/\.c$/.o/'`
|
||||
|
||||
# Create the lock directory.
|
||||
# Note: use '[/\\:.-]' here to ensure that we don't use the same name
|
||||
# that we are using for the .o file. Also, base the name on the expected
|
||||
# object file name, since that is what matters with a parallel build.
|
||||
lockdir=`echo "$cofile" | sed -e 's|[/\\:.-]|_|g'`.d
|
||||
while true; do
|
||||
if mkdir "$lockdir" >/dev/null 2>&1; then
|
||||
break
|
||||
fi
|
||||
sleep 1
|
||||
done
|
||||
# FIXME: race condition here if user kills between mkdir and trap.
|
||||
trap "rmdir '$lockdir'; exit 1" 1 2 15
|
||||
|
||||
# Run the compile.
|
||||
"$@"
|
||||
ret=$?
|
||||
|
||||
if test -f "$cofile"; then
|
||||
test "$cofile" = "$ofile" || mv "$cofile" "$ofile"
|
||||
elif test -f "${cofile}bj"; then
|
||||
test "${cofile}bj" = "$ofile" || mv "${cofile}bj" "$ofile"
|
||||
fi
|
||||
|
||||
rmdir "$lockdir"
|
||||
exit $ret
|
||||
|
||||
# Local Variables:
|
||||
# mode: shell-script
|
||||
# sh-indentation: 2
|
||||
# eval: (add-hook 'before-save-hook 'time-stamp)
|
||||
# time-stamp-start: "scriptversion="
|
||||
# time-stamp-format: "%:y-%02m-%02d.%02H"
|
||||
# time-stamp-time-zone: "UTC0"
|
||||
# time-stamp-end: "; # UTC"
|
||||
# End:
|
1480
trunk/3rdparty/gperftools-2-fit/config.guess
vendored
Executable file
1801
trunk/3rdparty/gperftools-2-fit/config.sub
vendored
Executable file
22674
trunk/3rdparty/gperftools-2-fit/configure
vendored
Executable file
657
trunk/3rdparty/gperftools-2-fit/configure.ac
vendored
Normal file
|
@ -0,0 +1,657 @@
|
|||
## Process this file with autoconf to produce configure.
|
||||
## In general, the safest way to proceed is to run ./autogen.sh
|
||||
|
||||
# make sure we're interpreted by some minimal autoconf
|
||||
AC_PREREQ([2.59])
|
||||
|
||||
AC_INIT([gperftools],[2.9.1],[gperftools@googlegroups.com])
|
||||
# Update this value for every release! (A:B:C will map to foo.so.(A-C).C.B)
|
||||
# http://www.gnu.org/software/libtool/manual/html_node/Updating-version-info.html
|
||||
TCMALLOC_SO_VERSION=9:9:5
|
||||
PROFILER_SO_VERSION=5:4:5
|
||||
TCMALLOC_AND_PROFILER_SO_VERSION=10:4:6
|
||||
|
||||
AC_SUBST(TCMALLOC_SO_VERSION)
|
||||
AC_SUBST(PROFILER_SO_VERSION)
|
||||
AC_SUBST(TCMALLOC_AND_PROFILER_SO_VERSION)
|
||||
|
||||
# The argument here is just something that should be in the current directory
|
||||
# (for sanity checking)
|
||||
AC_CONFIG_SRCDIR(README)
|
||||
AC_CONFIG_MACRO_DIR([m4])
|
||||
AC_CANONICAL_HOST
|
||||
AM_INIT_AUTOMAKE([dist-zip])
|
||||
AC_CONFIG_HEADERS([src/config.h])
|
||||
|
||||
AM_MAINTAINER_MODE()
|
||||
# Export the version information (for tc_version and friends)
|
||||
TC_VERSION_MAJOR=`expr "$PACKAGE_VERSION" : '\([[0-9]]*\)'`
|
||||
TC_VERSION_MINOR=`expr "$PACKAGE_VERSION" : '[[0-9]]*\.\([[0-9]]*\)'`
|
||||
TC_VERSION_PATCH=`expr "$PACKAGE_VERSION" : '[[0-9]]*\.[[0-9]]*\(.*\)$'`
|
||||
AC_SUBST(TC_VERSION_MAJOR)
|
||||
AC_SUBST(TC_VERSION_MINOR)
|
||||
AC_SUBST(TC_VERSION_PATCH)
|
||||
AC_SUBST(PACKAGE_STRING)
|
||||
|
||||
AX_GENERATE_CHANGELOG
|
||||
|
||||
# The user can choose not to compile in the heap-profiler, the
|
||||
# heap-checker, or the cpu-profiler. There's also the possibility
|
||||
# for a 'fully minimal' compile, which leaves out the stacktrace
|
||||
# code as well. By default, we include all of these that the
|
||||
# target system supports.
|
||||
default_enable_cpu_profiler=yes
|
||||
default_enable_heap_profiler=yes
|
||||
default_enable_heap_checker=yes
|
||||
default_enable_debugalloc=yes
|
||||
default_enable_minimal=no
|
||||
default_tcmalloc_alignment=16
|
||||
need_nanosleep=yes # Used later, to decide if to run ACX_NANOSLEEP
|
||||
case "$host" in
|
||||
*-mingw*) default_enable_minimal=yes; default_enable_debugalloc=no;
|
||||
need_nanosleep=no;;
|
||||
*-cygwin*) default_enable_heap_checker=no; default_enable_cpu_profiler=no;;
|
||||
*-freebsd*) default_enable_heap_checker=no;;
|
||||
*-darwin*) default_enable_heap_checker=no;;
|
||||
esac
|
||||
|
||||
# Currently only backtrace works on s390 and OSX.
|
||||
AC_COMPILE_IFELSE([AC_LANG_PROGRAM(, [
|
||||
#if !defined(__s390__) && !defined(__APPLE__)
|
||||
#error not s390 and not osx
|
||||
#endif
|
||||
return 1
|
||||
])],
|
||||
[default_enable_libunwind=no
|
||||
default_enable_backtrace=yes],
|
||||
[default_enable_libunwind=yes
|
||||
default_enable_backtrace=no])
|
||||
|
||||
# Disable libunwind linking on ppc64 by default.
|
||||
AC_COMPILE_IFELSE([AC_LANG_PROGRAM(, [return __PPC64__])],
|
||||
[default_enable_libunwind=no
|
||||
default_tcmalloc_pagesize=64],
|
||||
[default_enable_libunwind=yes
|
||||
default_tcmalloc_pagesize=8])
|
||||
|
||||
AC_ARG_ENABLE([cpu-profiler],
|
||||
[AS_HELP_STRING([--disable-cpu-profiler],
|
||||
[do not build the cpu profiler])],
|
||||
[],
|
||||
[enable_cpu_profiler="$default_enable_cpu_profiler"])
|
||||
AC_ARG_ENABLE([heap-profiler],
|
||||
[AS_HELP_STRING([--disable-heap-profiler],
|
||||
[do not build the heap profiler])],
|
||||
[],
|
||||
[enable_heap_profiler="$default_enable_heap_profiler"])
|
||||
AC_ARG_ENABLE([heap-checker],
|
||||
[AS_HELP_STRING([--disable-heap-checker],
|
||||
[do not build the heap checker])],
|
||||
[],
|
||||
[enable_heap_checker="$default_enable_heap_checker"])
|
||||
AC_ARG_ENABLE([debugalloc],
|
||||
[AS_HELP_STRING([--disable-debugalloc],
|
||||
[do not build versions of libs with debugalloc])],
|
||||
[],
|
||||
[enable_debugalloc="$default_enable_debugalloc"])
|
||||
AC_ARG_ENABLE([minimal],
|
||||
[AS_HELP_STRING([--enable-minimal],
|
||||
[build only tcmalloc-minimal (and maybe tcmalloc-minimal-debug)])],
|
||||
[],
|
||||
[enable_minimal="$default_enable_minimal"])
|
||||
if test "$enable_minimal" = yes; then
|
||||
enable_cpu_profiler=no
|
||||
enable_heap_profiler=no
|
||||
enable_heap_checker=no
|
||||
fi
|
||||
AC_ARG_ENABLE([stacktrace-via-backtrace],
|
||||
[AS_HELP_STRING([--enable-stacktrace-via-backtrace],
|
||||
[enable use of backtrace() for stacktrace capturing (may deadlock)])],
|
||||
[enable_backtrace=yes],
|
||||
[enable_backtrace="$default_enable_backtrace"])
|
||||
AC_ARG_ENABLE([libunwind],
|
||||
[AS_HELP_STRING([--enable-libunwind],
|
||||
[enable libunwind linking])],
|
||||
[],
|
||||
[enable_libunwind="$default_enable_libunwind"])
|
||||
AC_ARG_WITH([tcmalloc-pagesize],
|
||||
[AS_HELP_STRING([--with-tcmalloc-pagesize],
|
||||
[Set the tcmalloc internal page size to 4K, 8K, 16K, 32K, 64K, 128K or 256K])],
|
||||
[],
|
||||
[with_tcmalloc_pagesize=$default_tcmalloc_pagesize])
|
||||
AC_ARG_WITH([tcmalloc-alignment],
|
||||
[AS_HELP_STRING([--with-tcmalloc-alignment],
|
||||
[Set the tcmalloc allocation alignment to 8 or 16 bytes])],
|
||||
[],
|
||||
[with_tcmalloc_alignment=$default_tcmalloc_alignment])
|
||||
|
||||
case "$with_tcmalloc_pagesize" in
|
||||
4)
|
||||
AC_DEFINE(TCMALLOC_PAGE_SIZE_SHIFT, 12);;
|
||||
8)
|
||||
#Default tcmalloc page size.
|
||||
;;
|
||||
16)
|
||||
AC_DEFINE(TCMALLOC_PAGE_SIZE_SHIFT, 14);;
|
||||
32)
|
||||
AC_DEFINE(TCMALLOC_PAGE_SIZE_SHIFT, 15);;
|
||||
64)
|
||||
AC_DEFINE(TCMALLOC_PAGE_SIZE_SHIFT, 16);;
|
||||
128)
|
||||
AC_DEFINE(TCMALLOC_PAGE_SIZE_SHIFT, 17);;
|
||||
256)
|
||||
AC_DEFINE(TCMALLOC_PAGE_SIZE_SHIFT, 18,
|
||||
[Define internal page size for tcmalloc as number of left bitshift]);;
|
||||
*)
|
||||
AC_MSG_WARN([${with_tcmalloc_pagesize}K size not supported, using default tcmalloc page size.])
|
||||
esac
|
||||
case "$with_tcmalloc_alignment" in
|
||||
8)
|
||||
AC_DEFINE(TCMALLOC_ALIGN_8BYTES, 1,
|
||||
[Define 8 bytes of allocation alignment for tcmalloc]);;
|
||||
16)
|
||||
#Default tcmalloc allocation alignment.
|
||||
;;
|
||||
*)
|
||||
AC_MSG_WARN([${with_tcmalloc_alignment} bytes not supported, using default tcmalloc allocation alignment.])
|
||||
esac
|
||||
|
||||
# Checks for programs.
|
||||
AC_PROG_CXX
|
||||
AC_PROG_CC
|
||||
AC_PROG_CPP
|
||||
AM_CONDITIONAL(GCC, test "$GCC" = yes) # let the Makefile know if we're gcc
|
||||
AM_PROG_CC_C_O # shrug: autogen.sh suddenly needs this for some reason
|
||||
|
||||
AX_CXX_COMPILE_STDCXX(11, ext, mandatory)
|
||||
|
||||
# Check if we have an objcopy installed that supports -W
|
||||
AC_CHECK_TOOL([OBJCOPY], [objcopy], [])
|
||||
AS_IF([test -n "$OBJCOPY"], [dnl
|
||||
AC_CACHE_CHECK([if $OBJCOPY supports -W], gpt_cv_objcopy_weaken, [dnl
|
||||
AC_LINK_IFELSE([AC_LANG_PROGRAM([void foo() {} int main() {return 0;}])], [dnl
|
||||
AS_IF(["$OBJCOPY" -W foo conftest$ac_exeext /dev/null],
|
||||
[gpt_cv_objcopy_weaken=yes], [gpt_cv_objcopy_weaken=no])],
|
||||
[gpt_cv_objcopy_weaken=no])])],
|
||||
[gpt_cv_objcopy_weaken=no])
|
||||
AM_CONDITIONAL(HAVE_OBJCOPY_WEAKEN, test $gpt_cv_objcopy_weaken = yes)
|
||||
|
||||
AC_PROG_LIBTOOL
|
||||
|
||||
AX_C___ATTRIBUTE__
|
||||
|
||||
AC_MSG_CHECKING(for __attribute__((aligned(N))) on functions)
|
||||
AC_CACHE_VAL(ac_cv___attribute__aligned_fn, [
|
||||
AC_TRY_COMPILE(
|
||||
[#include <stdlib.h>
|
||||
void foo(void) __attribute__((aligned(128)));
|
||||
void foo(void) { exit(1); }],
|
||||
[],
|
||||
ac_cv___attribute__aligned_fn=yes,
|
||||
ac_cv___attribute__aligned_fn=no
|
||||
)])
|
||||
if test "$ac_cv___attribute__aligned_fn" = "yes"; then
|
||||
AC_DEFINE(HAVE___ATTRIBUTE__ALIGNED_FN, 1, [define if your compiler supports alignment of functions])
|
||||
fi
|
||||
AC_MSG_RESULT($ac_cv___attribute__aligned_fn)
|
||||
|
||||
|
||||
# Check whether some low-level functions/files are available
|
||||
AC_HEADER_STDC
|
||||
|
||||
# TODO(csilvers): we could remove a lot when WITH_CPU_PROFILER etc is "no".
|
||||
AC_CHECK_TYPES([struct mallinfo],,, [#include <malloc.h>])
|
||||
AC_CHECK_TYPES([Elf32_Versym],,, [#include <elf.h>]) # for vdso_support.h
|
||||
AC_CHECK_FUNCS(sbrk) # for tcmalloc to get memory
|
||||
AC_CHECK_FUNCS(__sbrk) # for tcmalloc to get memory
|
||||
AC_CHECK_FUNCS(geteuid) # for turning off services when run as root
|
||||
AC_CHECK_FUNCS(fork) # for the pthread_atfork setup
|
||||
AC_CHECK_HEADERS(features.h) # for vdso_support.h, __GLIBC__ macros
|
||||
AC_CHECK_HEADERS(malloc.h) # some systems define stuff there, others not
|
||||
AC_CHECK_HEADERS(glob.h) # for heap-profile-table (cleaning up profiles)
|
||||
AC_CHECK_HEADERS(execinfo.h) # for stacktrace? and heapchecker_unittest
|
||||
AC_CHECK_HEADERS(unwind.h) # for stacktrace
|
||||
AC_CHECK_HEADERS(sched.h) # for being nice in our spinlock code
|
||||
AC_CHECK_HEADERS(conflict-signal.h) # defined on some windows platforms?
|
||||
AC_CHECK_HEADERS(sys/prctl.h) # for thread_lister (needed by leak-checker)
|
||||
AC_CHECK_HEADERS(linux/ptrace.h)# also needed by leak-checker
|
||||
AC_CHECK_HEADERS(sys/syscall.h)
|
||||
AC_CHECK_HEADERS(sys/socket.h) # optional; for forking out to symbolizer
|
||||
AC_CHECK_HEADERS(sys/wait.h) # optional; for forking out to symbolizer
|
||||
AC_CHECK_HEADERS(poll.h) # optional; for forking out to symbolizer
|
||||
AC_CHECK_HEADERS(fcntl.h) # for tcmalloc_unittest
|
||||
AC_CHECK_HEADERS(grp.h) # for heapchecker_unittest
|
||||
AC_CHECK_HEADERS(pwd.h) # for heapchecker_unittest
|
||||
AC_CHECK_HEADERS(sys/resource.h) # for memalign_unittest.cc
|
||||
AC_CHECK_HEADERS(sys/cdefs.h) # Where glibc defines __THROW
|
||||
# We also need <ucontext.h>/<sys/ucontext.h>, but we get those from
|
||||
# AC_PC_FROM_UCONTEXT, below.
|
||||
|
||||
# We override a lot of memory allocation routines, not all of which are
|
||||
# standard. For those the system doesn't declare, we'll declare ourselves.
|
||||
AC_CHECK_DECLS([cfree,
|
||||
posix_memalign,
|
||||
memalign,
|
||||
valloc,
|
||||
pvalloc],,,
|
||||
[#define _XOPEN_SOURCE 600
|
||||
#include <stdlib.h>
|
||||
#include <malloc.h>])
|
||||
|
||||
if test "$ac_cv_type_struct_mallinfo" = yes; then
|
||||
AC_SUBST(ac_cv_have_struct_mallinfo, 1) # gperftools/tcmalloc.h needs this
|
||||
else
|
||||
AC_SUBST(ac_cv_have_struct_mallinfo, 0)
|
||||
fi
|
||||
|
||||
# We hardcode HAVE_MMAP to 1. There are no interesting systems anymore
|
||||
# without functional mmap. And our windows (except mingw) builds
|
||||
# aren't using autoconf. So we keep HAVE_MMAP define, but only to
|
||||
# distingush windows and rest.
|
||||
case "$host" in
|
||||
*-mingw*) default_emergency_malloc=no;;
|
||||
*) default_emergency_malloc=yes
|
||||
AC_DEFINE(HAVE_MMAP, 1, [Define to 1 if you have a working `mmap' system call.])
|
||||
esac
|
||||
|
||||
# If AtomicWord != Atomic32, we need to define two versions of all the
|
||||
# atomicops functions. If they're the same, we want to define only one.
|
||||
AC_MSG_CHECKING([if int32_t is the same type as intptr_t])
|
||||
AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[#include <stdint.h>]], [[int32_t v1 = 0; intptr_t v2 = 0; return (&v1 - &v2)]])],[AC_DEFINE(INT32_EQUALS_INTPTR, 1,
|
||||
Define to 1 if int32_t is equivalent to intptr_t)
|
||||
AC_MSG_RESULT([yes])],[AC_MSG_RESULT([no])])
|
||||
|
||||
# We want to access the "PC" (Program Counter) register from a struct
|
||||
# ucontext. Every system has its own way of doing that. We try all the
|
||||
# possibilities we know about. Note REG_PC should come first (REG_RIP
|
||||
# is also defined on solaris, but does the wrong thing). But don't
|
||||
# bother if we're not doing cpu-profiling.
|
||||
# [*] means that we've not actually tested one of these systems
|
||||
if test "$enable_cpu_profiler" = yes; then
|
||||
AC_PC_FROM_UCONTEXT(AC_MSG_WARN(Could not find the PC. Will not try to compile libprofiler...);
|
||||
enable_cpu_profiler=no)
|
||||
fi
|
||||
|
||||
# Some tests test the behavior of .so files, and only make sense for dynamic.
|
||||
AM_CONDITIONAL(ENABLE_STATIC, test "$enable_static" = yes)
|
||||
|
||||
# We want to link in libunwind if it is enabled and exists.
|
||||
UNWIND_LIBS=
|
||||
if test "$enable_libunwind" = yes; then
|
||||
AC_CHECK_HEADERS([libunwind.h],
|
||||
[AC_CHECK_LIB(unwind, backtrace, UNWIND_LIBS=-lunwind)
|
||||
will_use_libunwind=yes])
|
||||
fi
|
||||
AC_SUBST(UNWIND_LIBS)
|
||||
|
||||
# On x86_64, instead of libunwind, we can choose to compile with frame-pointers.
|
||||
AC_ARG_ENABLE(frame_pointers,
|
||||
AS_HELP_STRING([--enable-frame-pointers],
|
||||
[On x86_64 systems, compile with -fno-omit-frame-pointer (see INSTALL)]),
|
||||
, enable_frame_pointers=no)
|
||||
AM_CONDITIONAL(ENABLE_FRAME_POINTERS, test "$enable_frame_pointers" = yes)
|
||||
|
||||
AC_MSG_CHECKING([for x86 without frame pointers])
|
||||
AC_COMPILE_IFELSE([AC_LANG_PROGRAM(, [return __x86_64__ == 1 ? 0 : 1])],
|
||||
[is_x86_64=yes], [is_x86_64=no])
|
||||
omit_fp_by_default=no
|
||||
AS_IF([test "$is_x86_64" = yes], [omit_fp_by_default=yes])
|
||||
AM_CONDITIONAL(OMIT_FP_BY_DEFAULT,
|
||||
test "$omit_fp_by_default" = yes)
|
||||
AC_MSG_RESULT([$omit_fp_by_default])
|
||||
|
||||
# We need to know if we're i386 so we can turn on -mmms, which is not
|
||||
# on by default for i386 (it is for x86_64).
|
||||
AC_COMPILE_IFELSE([AC_LANG_PROGRAM(, [return __i386__ == 1 ? 0 : 1])],
|
||||
[is_i386=yes], [is_i386=no])
|
||||
AM_CONDITIONAL(I386, test "$is_i386" = yes)
|
||||
|
||||
# See if the compiler supports -Wno-unused-result.
|
||||
# Newer ubuntu's turn on -D_FORTIFY_SOURCE=2, enabling
|
||||
# __attribute__((warn_unused_result)) for things like write(),
|
||||
# which we don't care about.
|
||||
AC_CACHE_CHECK([if the compiler supports -Wno-unused-result],
|
||||
perftools_cv_w_no_unused_result,
|
||||
[OLD_CFLAGS="$CFLAGS"
|
||||
CFLAGS="$CFLAGS -Wno-error -Wunused-result"
|
||||
# gcc doesn't warn about unknown flags unless it's
|
||||
# also warning for some other purpose, hence the
|
||||
# divide-by-0. (We use -Wno-error to make sure the
|
||||
# divide-by-0 doesn't cause this test to fail!)
|
||||
#
|
||||
# Also gcc is giving only warning for unknown flags of
|
||||
# -Wno-XXX form. So in order to detect support we're
|
||||
# using -Wunused-result which will cause gcc to give
|
||||
# error which we can detect.
|
||||
AC_COMPILE_IFELSE([AC_LANG_PROGRAM(, return 1/0)],
|
||||
perftools_cv_w_no_unused_result=yes,
|
||||
perftools_cv_w_no_unused_result=no)
|
||||
CFLAGS="$OLD_CFLAGS"])
|
||||
AM_CONDITIONAL(HAVE_W_NO_UNUSED_RESULT,
|
||||
test "$perftools_cv_w_no_unused_result" = yes)
|
||||
|
||||
AC_ARG_ENABLE([deprecated-pprof],
|
||||
[AS_HELP_STRING([--disable-deprecated-pprof],
|
||||
[do not install old deprecated and unmaintained bundled pprof
|
||||
(see github.com/google/pprof for supported version)])],
|
||||
[enable_pprof="$enableval"],
|
||||
[enable_pprof=yes])
|
||||
|
||||
AM_CONDITIONAL(INSTALL_PPROF,
|
||||
[test "x$enable_pprof" = xyes])
|
||||
|
||||
AC_ARG_ENABLE([dynamic-sized-delete-support],
|
||||
[AS_HELP_STRING([--enable-dynamic-sized-delete-support],
|
||||
[try to build run-time switch for sized delete operator])],
|
||||
[enable_dyn_sized_delete="$enableval"],
|
||||
[enable_dyn_sized_delete=no])
|
||||
|
||||
AS_IF([test "x$enable_dyn_sized_delete" = xyes],
|
||||
[AC_DEFINE([ENABLE_DYNAMIC_SIZED_DELETE], 1,
|
||||
[Build runtime detection for sized delete])])
|
||||
|
||||
AC_ARG_ENABLE([sized-delete],
|
||||
[AS_HELP_STRING([--enable-sized-delete],
|
||||
[build sized delete operator])],
|
||||
[enable_sized_delete="$enableval"],
|
||||
[enable_sized_delete="no"])
|
||||
AS_IF([test "x$enable_sized_delete" = xyes],
|
||||
[AC_DEFINE([ENABLE_SIZED_DELETE], 1, [Build sized deletion operators])
|
||||
AC_MSG_NOTICE([Will build sized deallocation operators])],
|
||||
[AS_IF([test "x$enable_dyn_sized_delete" = xyes],
|
||||
[AC_MSG_NOTICE([Will build dynamically detected sized deallocation operators])],
|
||||
[AC_MSG_NOTICE([Will build sized deallocation operators that ignore size])])])
|
||||
|
||||
AC_CACHE_CHECK([if C++ compiler supports -fsized-deallocation],
|
||||
[perftools_cv_sized_deallocation_result],
|
||||
[AC_LANG_PUSH(C++)
|
||||
OLD_CXXFLAGS="$CXXFLAGS"
|
||||
CXXFLAGS="$CXXFLAGS -fsized-deallocation"
|
||||
AC_LINK_IFELSE([AC_LANG_PROGRAM(
|
||||
[[#include <new>
|
||||
#include <stddef.h>]],
|
||||
[[static void (* volatile ptr)(void *, size_t) = ::operator delete; (*ptr)(0, 256);]])],
|
||||
perftools_cv_sized_deallocation_result=yes,
|
||||
perftools_cv_sized_deallocation_result=no)
|
||||
CXXFLAGS="$OLD_CXXFLAGS"
|
||||
AC_LANG_POP(C++)])
|
||||
|
||||
AM_CONDITIONAL(HAVE_SIZED_DEALLOCATION,
|
||||
test "$perftools_cv_sized_deallocation_result" = yes)
|
||||
|
||||
AC_CACHE_CHECK([if C++ compiler supports std::align_val_t without options],
|
||||
[perftools_cv_have_align_val_t],
|
||||
[AC_LANG_PUSH(C++)
|
||||
AC_LINK_IFELSE([AC_LANG_PROGRAM(
|
||||
[[#include <new>]],
|
||||
[[(::operator delete)((::operator new)(256, std::align_val_t(16)), std::align_val_t(16))]])],
|
||||
perftools_cv_have_align_val_t=yes,
|
||||
perftools_cv_have_align_val_t=no)
|
||||
AC_LANG_POP(C++)])
|
||||
|
||||
AC_CACHE_CHECK([if C++ compiler supports -faligned-new],
|
||||
[perftools_cv_have_f_aligned_new],
|
||||
[AC_LANG_PUSH(C++)
|
||||
OLD_CXXFLAGS="$CXXFLAGS"
|
||||
CXXFLAGS="$CXXFLAGS -faligned-new"
|
||||
AC_LINK_IFELSE([AC_LANG_PROGRAM(
|
||||
[[#include <new>]],
|
||||
[[(::operator delete)((::operator new)(256, std::align_val_t(16)), std::align_val_t(16))]])],
|
||||
perftools_cv_have_f_aligned_new=yes,
|
||||
perftools_cv_have_f_aligned_new=no)
|
||||
CXXFLAGS="$OLD_CXXFLAGS"
|
||||
AC_LANG_POP(C++)])
|
||||
|
||||
AM_CONDITIONAL(HAVE_F_ALIGNED_NEW,
|
||||
test "$perftools_cv_have_f_aligned_new" = yes)
|
||||
|
||||
AS_IF([test "$perftools_cv_have_align_val_t" = yes || test "$perftools_cv_have_f_aligned_new" = yes],
|
||||
[AC_DEFINE([ENABLE_ALIGNED_NEW_DELETE], 1, [Build new/delete operators for overaligned types])
|
||||
AC_MSG_NOTICE([Will build new/delete operators for overaligned types])],
|
||||
AC_MSG_NOTICE([Will not build new/delete operators for overaligned types]))
|
||||
|
||||
if test "$perftools_cv_have_align_val_t" = yes || test "$perftools_cv_have_f_aligned_new" = yes; then
|
||||
AC_SUBST(ac_cv_have_std_align_val_t, 1) # gperftools/tcmalloc.h and windows/gperftools/tcmalloc.h need this
|
||||
else
|
||||
AC_SUBST(ac_cv_have_std_align_val_t, 0)
|
||||
fi
|
||||
|
||||
|
||||
AC_CACHE_CHECK([if target has _Unwind_Backtrace],
|
||||
[perftools_cv_have_unwind_backtrace],
|
||||
[AC_LANG_PUSH(C++)
|
||||
AC_COMPILE_IFELSE([AC_LANG_PROGRAM(
|
||||
[[#include <unwind.h>
|
||||
#if defined(__APPLE__)
|
||||
#error OSX _Unwind_Backtrace recurses back to malloc
|
||||
#endif
|
||||
]],
|
||||
[[&_Unwind_Backtrace]])],
|
||||
[perftools_cv_have_unwind_backtrace=yes],
|
||||
[perftools_cv_have_unwind_backtrace=no])
|
||||
AC_LANG_POP(C++)])
|
||||
AS_IF([test "x$perftools_cv_have_unwind_backtrace" = xyes],
|
||||
[AC_DEFINE(HAVE_UNWIND_BACKTRACE, 1, [Whether <unwind.h> contains _Unwind_Backtrace])])
|
||||
|
||||
AS_IF([test "x$will_use_libunwind" = xyes],
|
||||
[AC_COMPILE_IFELSE([AC_LANG_PROGRAM(, [return __arm__])],
|
||||
[default_emergency_malloc=yes])])
|
||||
|
||||
AC_ARG_ENABLE([emergency-malloc],
|
||||
[AS_HELP_STRING([--enable-emergency-malloc],
|
||||
[build emergency malloc feature])],
|
||||
[enable_emergency_malloc="$enableval"],
|
||||
[enable_emergency_malloc="$default_emergency_malloc"])
|
||||
|
||||
AM_CONDITIONAL(BUILD_EMERGENCY_MALLOC, [test "x$enable_emergency_malloc" = xyes])
|
||||
|
||||
# Also make sure we get standard PRI... definitions, even with glibc.
|
||||
# We have to use AH_VERBATIM because we need the #ifdef guard (gcc buglet)
|
||||
AH_VERBATIM([__STDC_FORMAT_MACROS],
|
||||
[/* C99 says: define this to get the PRI... macros from stdint.h */
|
||||
#ifndef __STDC_FORMAT_MACROS
|
||||
# define __STDC_FORMAT_MACROS 1
|
||||
#endif])
|
||||
|
||||
# Check if __environ is available (for GetenvBeforeMain)
|
||||
AC_MSG_CHECKING([for __environ])
|
||||
AC_LINK_IFELSE([AC_LANG_PROGRAM([#include <unistd.h>],
|
||||
[char **env = __environ])],
|
||||
[AC_DEFINE(HAVE___ENVIRON, 1,
|
||||
[Define to 1 if compiler supports __environ])
|
||||
AC_MSG_RESULT([yes])],
|
||||
[AC_MSG_RESULT([no])])
|
||||
|
||||
# If we support __thread, that can speed up tcmalloc a bit.
|
||||
# Note, however, that our code tickles a bug in gcc < 4.1.2
|
||||
# involving TLS and -fPIC (which our libraries will use) on x86:
|
||||
# http://gcc.gnu.org/ml/gcc-bugs/2006-09/msg02275.html
|
||||
#
|
||||
# And mingw also does compile __thread but resultant code actually
|
||||
# fails to work correctly at least in some not so ancient version:
|
||||
# http://mingw-users.1079350.n2.nabble.com/gcc-4-4-multi-threaded-exception-handling-amp-thread-specifier-not-working-td3440749.html
|
||||
#
|
||||
# Also it was reported that earlier gcc versions for mips compile
|
||||
# __thread but it doesn't really work
|
||||
AC_MSG_CHECKING([for __thread])
|
||||
AC_LINK_IFELSE([AC_LANG_PROGRAM([#if defined(__GNUC__) && ((__GNUC__ < 4) || (__GNUC__ == 4 && __GNUC_MINOR__ < 1) || (__GNUC__ == 4 && __GNUC_MINOR__ == 1 && __GNUC_PATCHLEVEL__ < 2))
|
||||
#error gcc has this bug: http://gcc.gnu.org/ml/gcc-bugs/2006-09/msg02275.html
|
||||
#elif defined(__MINGW32__)
|
||||
#error mingw doesnt really support tls
|
||||
#elif defined(__APPLE__)
|
||||
#error OSX __thread support is known to call malloc which makes it unsafe to use from malloc replacement
|
||||
#endif
|
||||
], [static __thread int p = 0])],
|
||||
[AC_DEFINE(HAVE_TLS, 1,
|
||||
Define to 1 if compiler supports __thread)
|
||||
AC_MSG_RESULT([yes])],
|
||||
[AC_MSG_RESULT([no])])
|
||||
|
||||
# Nanosleep requires extra libraries on some architectures (solaris).
|
||||
# This sets NANOSLEEP_LIBS. nanosleep doesn't exist on mingw, which
|
||||
# is fine for us because we don't compile libspinlock, which uses it.
|
||||
if test "$need_nanosleep" = yes; then
|
||||
ACX_NANOSLEEP
|
||||
AC_SUBST(NANOSLEEP_LIBS)
|
||||
fi
|
||||
|
||||
# Solaris 10 6/06 has a bug where /usr/sfw/lib/libstdc++.la is empty.
|
||||
# If so, we replace it with our own version.
|
||||
LIBSTDCXX_LA_LINKER_FLAG=
|
||||
if test -f /usr/sfw/lib/libstdc++.la && ! test -s /usr/sfw/lib/libstdc++.la
|
||||
then
|
||||
LIBSTDCXX_LA_LINKER_FLAG='-L$(top_srcdir)/src/solaris'
|
||||
fi
|
||||
AC_SUBST(LIBSTDCXX_LA_LINKER_FLAG)
|
||||
|
||||
# In fact, a lot of the code in this directory depends on pthreads
|
||||
ACX_PTHREAD
|
||||
|
||||
AC_LANG_SAVE
|
||||
AC_LANG_CPLUSPLUS
|
||||
AC_MSG_CHECKING([whether pthread symbols are available in C++ without including pthread.h])
|
||||
acx_pthread_despite_asking_for=no
|
||||
AC_LINK_IFELSE(
|
||||
[AC_LANG_PROGRAM([
|
||||
#include <string>
|
||||
#include <vector>
|
||||
],[
|
||||
pthread_t th; pthread_join(th, 0);
|
||||
])],[
|
||||
acx_pthread_despite_asking_for=yes
|
||||
AC_DEFINE(HAVE_PTHREAD_DESPITE_ASKING_FOR, 1, [defined to 1 if pthread symbols are exposed even without include pthread.h])
|
||||
AC_DEFINE(HAVE_PTHREAD, 1, [])
|
||||
])
|
||||
AC_MSG_RESULT([$acx_pthread_despite_asking_for])
|
||||
AC_LANG_RESTORE
|
||||
|
||||
AM_CONDITIONAL(HAVE_PTHREAD_DESPITE_ASKING_FOR, test x"$acx_pthread_despite_asking_for" = xyes)
|
||||
|
||||
# Figure out where libc has program_invocation_name
|
||||
AC_PROGRAM_INVOCATION_NAME
|
||||
|
||||
# Make the install prefix available, to figure out where to look for pprof
|
||||
AC_INSTALL_PREFIX
|
||||
|
||||
dnl only very recent mingw has sleep and nanosleep
|
||||
case "$host" in
|
||||
*-mingw*)
|
||||
AC_CHECK_DECLS([sleep], [], [], [#include <unistd.h>])
|
||||
AC_CHECK_DECLS([nanosleep], [], [], [#include <time.h>])
|
||||
;;
|
||||
esac
|
||||
|
||||
if test "x$enable_backtrace" = xyes; then
|
||||
AC_CHECK_DECLS([backtrace], [], [], [#include <execinfo.h>])
|
||||
save_LIBS=$LIBS
|
||||
LIBS=$UNWIND_LIBS
|
||||
AC_SEARCH_LIBS([backtrace], [execinfo])
|
||||
UNWIND_LIBS=$LIBS
|
||||
LIBS=$save_LIBS
|
||||
fi
|
||||
|
||||
# For windows, this has a non-trivial value (__declspec(export)), but any
|
||||
# system that uses configure wants this to be the empty string.
|
||||
AC_DEFINE(PERFTOOLS_DLL_DECL,,
|
||||
[Always the empty-string on non-windows systems.
|
||||
On windows, should be "__declspec(dllexport)".
|
||||
This way, when we compile the dll, we export our functions/classes.
|
||||
It's safe to define this here because config.h is only used
|
||||
internally, to compile the DLL, and every DLL source file
|
||||
#includes "config.h" before anything else.])
|
||||
|
||||
# In theory, config.h files shouldn't need a header guard, but we do,
|
||||
# because we (maybe) #include windows/mingw.h from within config.h,
|
||||
# and it #includes other .h files. These all have header guards, so
|
||||
# the end result is if config.h is #included twice, its #undefs get
|
||||
# evaluated twice, but all the ones in mingw.h/etc only get evaluated
|
||||
# once, potentially causing trouble. c.f.
|
||||
# http://code.google.com/p/gperftools/issues/detail?id=246
|
||||
AH_TOP([
|
||||
#ifndef GPERFTOOLS_CONFIG_H_
|
||||
#define GPERFTOOLS_CONFIG_H_
|
||||
])
|
||||
|
||||
AH_VERBATIM([PTHREADS_CRASHES_IF_RUN_TOO_EARLY],
|
||||
[/* Mark the systems where we know it's bad if pthreads runs too
|
||||
early before main (before threads are initialized, presumably). */
|
||||
#ifdef __FreeBSD__
|
||||
#define PTHREADS_CRASHES_IF_RUN_TOO_EARLY 1
|
||||
#endif])
|
||||
|
||||
# MinGW uses autoconf, but also needs the windows shim routines
|
||||
# (since it doesn't have its own support for, say, pthreads).
|
||||
# This requires us to #include a special header file, and also to
|
||||
# link in some windows versions of .o's instead of the unix versions.
|
||||
#
|
||||
# Also, manually mark systems where we have to be careful how early
|
||||
# we run pthreads. TODO(csilvers): turn this into an autoconf check.
|
||||
AH_BOTTOM([
|
||||
#ifdef __MINGW32__
|
||||
#include "windows/mingw.h"
|
||||
#endif
|
||||
|
||||
#endif /* #ifndef GPERFTOOLS_CONFIG_H_ */
|
||||
])
|
||||
AM_CONDITIONAL(MINGW, expr $host : '.*-mingw' >/dev/null 2>&1)
|
||||
AM_CONDITIONAL(OSX, expr $host : '.*-apple-darwin.*' >/dev/null 2>&1)
|
||||
|
||||
# Export the --enable flags we set above. We do this at the end so
|
||||
# other configure rules can enable or disable targets based on what
|
||||
# they find.
|
||||
AM_CONDITIONAL(WITH_CPU_PROFILER, test "$enable_cpu_profiler" = yes)
|
||||
AM_CONDITIONAL(WITH_HEAP_PROFILER, test "$enable_heap_profiler" = yes)
|
||||
AM_CONDITIONAL(WITH_HEAP_CHECKER, test "$enable_heap_checker" = yes)
|
||||
AM_CONDITIONAL(WITH_DEBUGALLOC, test "$enable_debugalloc" = yes)
|
||||
# We make tcmalloc.so if either heap-profiler or heap-checker is asked for.
|
||||
AM_CONDITIONAL(WITH_HEAP_PROFILER_OR_CHECKER,
|
||||
test "$enable_heap_profiler" = yes -o \
|
||||
"$enable_heap_checker" = yes)
|
||||
# If we don't use any profilers, we don't need stack traces (or pprof)
|
||||
AM_CONDITIONAL(WITH_STACK_TRACE, test "$enable_cpu_profiler" = yes -o \
|
||||
"$enable_heap_profiler" = yes -o \
|
||||
"$enable_heap_checker" = yes)
|
||||
|
||||
have_linux_sigev_thread_id=no
|
||||
AC_MSG_CHECKING([for Linux SIGEV_THREAD_ID])
|
||||
AC_COMPILE_IFELSE(
|
||||
[AC_LANG_PROGRAM([[#include <signal.h>
|
||||
#include <time.h>]],
|
||||
[[return SIGEV_THREAD_ID || CLOCK_THREAD_CPUTIME_ID || __linux;]])],
|
||||
[AC_DEFINE(HAVE_LINUX_SIGEV_THREAD_ID, 1,
|
||||
[Define if this is Linux that has SIGEV_THREAD_ID])
|
||||
have_linux_sigev_thread_id=yes
|
||||
AC_MSG_RESULT([yes])],
|
||||
[AC_MSG_RESULT([no])])
|
||||
|
||||
# Disable large allocation report by default.
|
||||
AC_ARG_ENABLE([large-alloc-report],
|
||||
[AS_HELP_STRING([--enable-large-alloc-report],
|
||||
[report very large allocations to stderr])],
|
||||
[enable_large_alloc_report="$enableval"],
|
||||
[enable_large_alloc_report=no])
|
||||
AS_IF([test "x$enable_large_alloc_report" = xyes],
|
||||
[AC_DEFINE([ENABLE_LARGE_ALLOC_REPORT], 1, [report large allocation])])
|
||||
|
||||
# Enable aggressive decommit by default
|
||||
AC_ARG_ENABLE([aggressive-decommit-by-default],
|
||||
[AS_HELP_STRING([--enable-aggressive-decommit-by-default],
|
||||
[enable aggressive decommit by default])],
|
||||
[enable_aggressive_decommit_by_default="$enableval"],
|
||||
[enable_aggressive_decommit_by_default=no])
|
||||
AS_IF([test "x$enable_aggressive_decommit_by_default" = xyes],
|
||||
[AC_DEFINE([ENABLE_AGGRESSIVE_DECOMMIT_BY_DEFAULT],
|
||||
1,
|
||||
[enable aggressive decommit by default])])
|
||||
|
||||
# Write generated configuration file
|
||||
AC_CONFIG_FILES([Makefile
|
||||
src/gperftools/tcmalloc.h src/windows/gperftools/tcmalloc.h])
|
||||
AC_OUTPUT
|
||||
|
||||
AS_IF([test "$omit_fp_by_default" = yes && test "x$enable_frame_pointers" != xyes && test "x$UNWIND_LIBS" = x && test "x$enable_minimal" != xyes],
|
||||
[AS_IF([test "x$perftools_cv_have_unwind_backtrace" = xyes],
|
||||
[AC_MSG_WARN([No frame pointers and no libunwind. Using experimental backtrace capturing via libgcc. Expect crashy cpu profiler.])],
|
||||
[AS_IF([test "x$enable_backtrace" = xyes],
|
||||
[AC_MSG_WARN([No frame pointers and no libunwind. Using experimental backtrace(). Expect crashy cpu profiler.])],
|
||||
[AC_MSG_FAILURE([No frame pointers and no libunwind. The compilation will fail])])])])
|
791
trunk/3rdparty/gperftools-2-fit/depcomp
vendored
Executable file
|
@ -0,0 +1,791 @@
|
|||
#! /bin/sh
|
||||
# depcomp - compile a program generating dependencies as side-effects
|
||||
|
||||
scriptversion=2018-03-07.03; # UTC
|
||||
|
||||
# Copyright (C) 1999-2020 Free Software Foundation, Inc.
|
||||
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; either version 2, or (at your option)
|
||||
# any later version.
|
||||
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
|
||||
# As a special exception to the GNU General Public License, if you
|
||||
# distribute this file as part of a program that contains a
|
||||
# configuration script generated by Autoconf, you may include it under
|
||||
# the same distribution terms that you use for the rest of that program.
|
||||
|
||||
# Originally written by Alexandre Oliva <oliva@dcc.unicamp.br>.
|
||||
|
||||
case $1 in
|
||||
'')
|
||||
echo "$0: No command. Try '$0 --help' for more information." 1>&2
|
||||
exit 1;
|
||||
;;
|
||||
-h | --h*)
|
||||
cat <<\EOF
|
||||
Usage: depcomp [--help] [--version] PROGRAM [ARGS]
|
||||
|
||||
Run PROGRAMS ARGS to compile a file, generating dependencies
|
||||
as side-effects.
|
||||
|
||||
Environment variables:
|
||||
depmode Dependency tracking mode.
|
||||
source Source file read by 'PROGRAMS ARGS'.
|
||||
object Object file output by 'PROGRAMS ARGS'.
|
||||
DEPDIR directory where to store dependencies.
|
||||
depfile Dependency file to output.
|
||||
tmpdepfile Temporary file to use when outputting dependencies.
|
||||
libtool Whether libtool is used (yes/no).
|
||||
|
||||
Report bugs to <bug-automake@gnu.org>.
|
||||
EOF
|
||||
exit $?
|
||||
;;
|
||||
-v | --v*)
|
||||
echo "depcomp $scriptversion"
|
||||
exit $?
|
||||
;;
|
||||
esac
|
||||
|
||||
# Get the directory component of the given path, and save it in the
|
||||
# global variables '$dir'. Note that this directory component will
|
||||
# be either empty or ending with a '/' character. This is deliberate.
|
||||
set_dir_from ()
|
||||
{
|
||||
case $1 in
|
||||
*/*) dir=`echo "$1" | sed -e 's|/[^/]*$|/|'`;;
|
||||
*) dir=;;
|
||||
esac
|
||||
}
|
||||
|
||||
# Get the suffix-stripped basename of the given path, and save it the
|
||||
# global variable '$base'.
|
||||
set_base_from ()
|
||||
{
|
||||
base=`echo "$1" | sed -e 's|^.*/||' -e 's/\.[^.]*$//'`
|
||||
}
|
||||
|
||||
# If no dependency file was actually created by the compiler invocation,
|
||||
# we still have to create a dummy depfile, to avoid errors with the
|
||||
# Makefile "include basename.Plo" scheme.
|
||||
make_dummy_depfile ()
|
||||
{
|
||||
echo "#dummy" > "$depfile"
|
||||
}
|
||||
|
||||
# Factor out some common post-processing of the generated depfile.
|
||||
# Requires the auxiliary global variable '$tmpdepfile' to be set.
|
||||
aix_post_process_depfile ()
|
||||
{
|
||||
# If the compiler actually managed to produce a dependency file,
|
||||
# post-process it.
|
||||
if test -f "$tmpdepfile"; then
|
||||
# Each line is of the form 'foo.o: dependency.h'.
|
||||
# Do two passes, one to just change these to
|
||||
# $object: dependency.h
|
||||
# and one to simply output
|
||||
# dependency.h:
|
||||
# which is needed to avoid the deleted-header problem.
|
||||
{ sed -e "s,^.*\.[$lower]*:,$object:," < "$tmpdepfile"
|
||||
sed -e "s,^.*\.[$lower]*:[$tab ]*,," -e 's,$,:,' < "$tmpdepfile"
|
||||
} > "$depfile"
|
||||
rm -f "$tmpdepfile"
|
||||
else
|
||||
make_dummy_depfile
|
||||
fi
|
||||
}
|
||||
|
||||
# A tabulation character.
|
||||
tab=' '
|
||||
# A newline character.
|
||||
nl='
|
||||
'
|
||||
# Character ranges might be problematic outside the C locale.
|
||||
# These definitions help.
|
||||
upper=ABCDEFGHIJKLMNOPQRSTUVWXYZ
|
||||
lower=abcdefghijklmnopqrstuvwxyz
|
||||
digits=0123456789
|
||||
alpha=${upper}${lower}
|
||||
|
||||
if test -z "$depmode" || test -z "$source" || test -z "$object"; then
|
||||
echo "depcomp: Variables source, object and depmode must be set" 1>&2
|
||||
exit 1
|
||||
fi
|
||||
|
||||
# Dependencies for sub/bar.o or sub/bar.obj go into sub/.deps/bar.Po.
|
||||
depfile=${depfile-`echo "$object" |
|
||||
sed 's|[^\\/]*$|'${DEPDIR-.deps}'/&|;s|\.\([^.]*\)$|.P\1|;s|Pobj$|Po|'`}
|
||||
tmpdepfile=${tmpdepfile-`echo "$depfile" | sed 's/\.\([^.]*\)$/.T\1/'`}
|
||||
|
||||
rm -f "$tmpdepfile"
|
||||
|
||||
# Avoid interferences from the environment.
|
||||
gccflag= dashmflag=
|
||||
|
||||
# Some modes work just like other modes, but use different flags. We
|
||||
# parameterize here, but still list the modes in the big case below,
|
||||
# to make depend.m4 easier to write. Note that we *cannot* use a case
|
||||
# here, because this file can only contain one case statement.
|
||||
if test "$depmode" = hp; then
|
||||
# HP compiler uses -M and no extra arg.
|
||||
gccflag=-M
|
||||
depmode=gcc
|
||||
fi
|
||||
|
||||
if test "$depmode" = dashXmstdout; then
|
||||
# This is just like dashmstdout with a different argument.
|
||||
dashmflag=-xM
|
||||
depmode=dashmstdout
|
||||
fi
|
||||
|
||||
cygpath_u="cygpath -u -f -"
|
||||
if test "$depmode" = msvcmsys; then
|
||||
# This is just like msvisualcpp but w/o cygpath translation.
|
||||
# Just convert the backslash-escaped backslashes to single forward
|
||||
# slashes to satisfy depend.m4
|
||||
cygpath_u='sed s,\\\\,/,g'
|
||||
depmode=msvisualcpp
|
||||
fi
|
||||
|
||||
if test "$depmode" = msvc7msys; then
|
||||
# This is just like msvc7 but w/o cygpath translation.
|
||||
# Just convert the backslash-escaped backslashes to single forward
|
||||
# slashes to satisfy depend.m4
|
||||
cygpath_u='sed s,\\\\,/,g'
|
||||
depmode=msvc7
|
||||
fi
|
||||
|
||||
if test "$depmode" = xlc; then
|
||||
# IBM C/C++ Compilers xlc/xlC can output gcc-like dependency information.
|
||||
gccflag=-qmakedep=gcc,-MF
|
||||
depmode=gcc
|
||||
fi
|
||||
|
||||
case "$depmode" in
|
||||
gcc3)
|
||||
## gcc 3 implements dependency tracking that does exactly what
|
||||
## we want. Yay! Note: for some reason libtool 1.4 doesn't like
|
||||
## it if -MD -MP comes after the -MF stuff. Hmm.
|
||||
## Unfortunately, FreeBSD c89 acceptance of flags depends upon
|
||||
## the command line argument order; so add the flags where they
|
||||
## appear in depend2.am. Note that the slowdown incurred here
|
||||
## affects only configure: in makefiles, %FASTDEP% shortcuts this.
|
||||
for arg
|
||||
do
|
||||
case $arg in
|
||||
-c) set fnord "$@" -MT "$object" -MD -MP -MF "$tmpdepfile" "$arg" ;;
|
||||
*) set fnord "$@" "$arg" ;;
|
||||
esac
|
||||
shift # fnord
|
||||
shift # $arg
|
||||
done
|
||||
"$@"
|
||||
stat=$?
|
||||
if test $stat -ne 0; then
|
||||
rm -f "$tmpdepfile"
|
||||
exit $stat
|
||||
fi
|
||||
mv "$tmpdepfile" "$depfile"
|
||||
;;
|
||||
|
||||
gcc)
|
||||
## Note that this doesn't just cater to obsosete pre-3.x GCC compilers.
|
||||
## but also to in-use compilers like IMB xlc/xlC and the HP C compiler.
|
||||
## (see the conditional assignment to $gccflag above).
|
||||
## There are various ways to get dependency output from gcc. Here's
|
||||
## why we pick this rather obscure method:
|
||||
## - Don't want to use -MD because we'd like the dependencies to end
|
||||
## up in a subdir. Having to rename by hand is ugly.
|
||||
## (We might end up doing this anyway to support other compilers.)
|
||||
## - The DEPENDENCIES_OUTPUT environment variable makes gcc act like
|
||||
## -MM, not -M (despite what the docs say). Also, it might not be
|
||||
## supported by the other compilers which use the 'gcc' depmode.
|
||||
## - Using -M directly means running the compiler twice (even worse
|
||||
## than renaming).
|
||||
if test -z "$gccflag"; then
|
||||
gccflag=-MD,
|
||||
fi
|
||||
"$@" -Wp,"$gccflag$tmpdepfile"
|
||||
stat=$?
|
||||
if test $stat -ne 0; then
|
||||
rm -f "$tmpdepfile"
|
||||
exit $stat
|
||||
fi
|
||||
rm -f "$depfile"
|
||||
echo "$object : \\" > "$depfile"
|
||||
# The second -e expression handles DOS-style file names with drive
|
||||
# letters.
|
||||
sed -e 's/^[^:]*: / /' \
|
||||
-e 's/^['$alpha']:\/[^:]*: / /' < "$tmpdepfile" >> "$depfile"
|
||||
## This next piece of magic avoids the "deleted header file" problem.
|
||||
## The problem is that when a header file which appears in a .P file
|
||||
## is deleted, the dependency causes make to die (because there is
|
||||
## typically no way to rebuild the header). We avoid this by adding
|
||||
## dummy dependencies for each header file. Too bad gcc doesn't do
|
||||
## this for us directly.
|
||||
## Some versions of gcc put a space before the ':'. On the theory
|
||||
## that the space means something, we add a space to the output as
|
||||
## well. hp depmode also adds that space, but also prefixes the VPATH
|
||||
## to the object. Take care to not repeat it in the output.
|
||||
## Some versions of the HPUX 10.20 sed can't process this invocation
|
||||
## correctly. Breaking it into two sed invocations is a workaround.
|
||||
tr ' ' "$nl" < "$tmpdepfile" \
|
||||
| sed -e 's/^\\$//' -e '/^$/d' -e "s|.*$object$||" -e '/:$/d' \
|
||||
| sed -e 's/$/ :/' >> "$depfile"
|
||||
rm -f "$tmpdepfile"
|
||||
;;
|
||||
|
||||
hp)
|
||||
# This case exists only to let depend.m4 do its work. It works by
|
||||
# looking at the text of this script. This case will never be run,
|
||||
# since it is checked for above.
|
||||
exit 1
|
||||
;;
|
||||
|
||||
sgi)
|
||||
if test "$libtool" = yes; then
|
||||
"$@" "-Wp,-MDupdate,$tmpdepfile"
|
||||
else
|
||||
"$@" -MDupdate "$tmpdepfile"
|
||||
fi
|
||||
stat=$?
|
||||
if test $stat -ne 0; then
|
||||
rm -f "$tmpdepfile"
|
||||
exit $stat
|
||||
fi
|
||||
rm -f "$depfile"
|
||||
|
||||
if test -f "$tmpdepfile"; then # yes, the sourcefile depend on other files
|
||||
echo "$object : \\" > "$depfile"
|
||||
# Clip off the initial element (the dependent). Don't try to be
|
||||
# clever and replace this with sed code, as IRIX sed won't handle
|
||||
# lines with more than a fixed number of characters (4096 in
|
||||
# IRIX 6.2 sed, 8192 in IRIX 6.5). We also remove comment lines;
|
||||
# the IRIX cc adds comments like '#:fec' to the end of the
|
||||
# dependency line.
|
||||
tr ' ' "$nl" < "$tmpdepfile" \
|
||||
| sed -e 's/^.*\.o://' -e 's/#.*$//' -e '/^$/ d' \
|
||||
| tr "$nl" ' ' >> "$depfile"
|
||||
echo >> "$depfile"
|
||||
# The second pass generates a dummy entry for each header file.
|
||||
tr ' ' "$nl" < "$tmpdepfile" \
|
||||
| sed -e 's/^.*\.o://' -e 's/#.*$//' -e '/^$/ d' -e 's/$/:/' \
|
||||
>> "$depfile"
|
||||
else
|
||||
make_dummy_depfile
|
||||
fi
|
||||
rm -f "$tmpdepfile"
|
||||
;;
|
||||
|
||||
xlc)
|
||||
# This case exists only to let depend.m4 do its work. It works by
|
||||
# looking at the text of this script. This case will never be run,
|
||||
# since it is checked for above.
|
||||
exit 1
|
||||
;;
|
||||
|
||||
aix)
|
||||
# The C for AIX Compiler uses -M and outputs the dependencies
|
||||
# in a .u file. In older versions, this file always lives in the
|
||||
# current directory. Also, the AIX compiler puts '$object:' at the
|
||||
# start of each line; $object doesn't have directory information.
|
||||
# Version 6 uses the directory in both cases.
|
||||
set_dir_from "$object"
|
||||
set_base_from "$object"
|
||||
if test "$libtool" = yes; then
|
||||
tmpdepfile1=$dir$base.u
|
||||
tmpdepfile2=$base.u
|
||||
tmpdepfile3=$dir.libs/$base.u
|
||||
"$@" -Wc,-M
|
||||
else
|
||||
tmpdepfile1=$dir$base.u
|
||||
tmpdepfile2=$dir$base.u
|
||||
tmpdepfile3=$dir$base.u
|
||||
"$@" -M
|
||||
fi
|
||||
stat=$?
|
||||
if test $stat -ne 0; then
|
||||
rm -f "$tmpdepfile1" "$tmpdepfile2" "$tmpdepfile3"
|
||||
exit $stat
|
||||
fi
|
||||
|
||||
for tmpdepfile in "$tmpdepfile1" "$tmpdepfile2" "$tmpdepfile3"
|
||||
do
|
||||
test -f "$tmpdepfile" && break
|
||||
done
|
||||
aix_post_process_depfile
|
||||
;;
|
||||
|
||||
tcc)
|
||||
# tcc (Tiny C Compiler) understand '-MD -MF file' since version 0.9.26
|
||||
# FIXME: That version still under development at the moment of writing.
|
||||
# Make that this statement remains true also for stable, released
|
||||
# versions.
|
||||
# It will wrap lines (doesn't matter whether long or short) with a
|
||||
# trailing '\', as in:
|
||||
#
|
||||
# foo.o : \
|
||||
# foo.c \
|
||||
# foo.h \
|
||||
#
|
||||
# It will put a trailing '\' even on the last line, and will use leading
|
||||
# spaces rather than leading tabs (at least since its commit 0394caf7
|
||||
# "Emit spaces for -MD").
|
||||
"$@" -MD -MF "$tmpdepfile"
|
||||
stat=$?
|
||||
if test $stat -ne 0; then
|
||||
rm -f "$tmpdepfile"
|
||||
exit $stat
|
||||
fi
|
||||
rm -f "$depfile"
|
||||
# Each non-empty line is of the form 'foo.o : \' or ' dep.h \'.
|
||||
# We have to change lines of the first kind to '$object: \'.
|
||||
sed -e "s|.*:|$object :|" < "$tmpdepfile" > "$depfile"
|
||||
# And for each line of the second kind, we have to emit a 'dep.h:'
|
||||
# dummy dependency, to avoid the deleted-header problem.
|
||||
sed -n -e 's|^ *\(.*\) *\\$|\1:|p' < "$tmpdepfile" >> "$depfile"
|
||||
rm -f "$tmpdepfile"
|
||||
;;
|
||||
|
||||
## The order of this option in the case statement is important, since the
|
||||
## shell code in configure will try each of these formats in the order
|
||||
## listed in this file. A plain '-MD' option would be understood by many
|
||||
## compilers, so we must ensure this comes after the gcc and icc options.
|
||||
pgcc)
|
||||
# Portland's C compiler understands '-MD'.
|
||||
# Will always output deps to 'file.d' where file is the root name of the
|
||||
# source file under compilation, even if file resides in a subdirectory.
|
||||
# The object file name does not affect the name of the '.d' file.
|
||||
# pgcc 10.2 will output
|
||||
# foo.o: sub/foo.c sub/foo.h
|
||||
# and will wrap long lines using '\' :
|
||||
# foo.o: sub/foo.c ... \
|
||||
# sub/foo.h ... \
|
||||
# ...
|
||||
set_dir_from "$object"
|
||||
# Use the source, not the object, to determine the base name, since
|
||||
# that's sadly what pgcc will do too.
|
||||
set_base_from "$source"
|
||||
tmpdepfile=$base.d
|
||||
|
||||
# For projects that build the same source file twice into different object
|
||||
# files, the pgcc approach of using the *source* file root name can cause
|
||||
# problems in parallel builds. Use a locking strategy to avoid stomping on
|
||||
# the same $tmpdepfile.
|
||||
lockdir=$base.d-lock
|
||||
trap "
|
||||
echo '$0: caught signal, cleaning up...' >&2
|
||||
rmdir '$lockdir'
|
||||
exit 1
|
||||
" 1 2 13 15
|
||||
numtries=100
|
||||
i=$numtries
|
||||
while test $i -gt 0; do
|
||||
# mkdir is a portable test-and-set.
|
||||
if mkdir "$lockdir" 2>/dev/null; then
|
||||
# This process acquired the lock.
|
||||
"$@" -MD
|
||||
stat=$?
|
||||
# Release the lock.
|
||||
rmdir "$lockdir"
|
||||
break
|
||||
else
|
||||
# If the lock is being held by a different process, wait
|
||||
# until the winning process is done or we timeout.
|
||||
while test -d "$lockdir" && test $i -gt 0; do
|
||||
sleep 1
|
||||
i=`expr $i - 1`
|
||||
done
|
||||
fi
|
||||
i=`expr $i - 1`
|
||||
done
|
||||
trap - 1 2 13 15
|
||||
if test $i -le 0; then
|
||||
echo "$0: failed to acquire lock after $numtries attempts" >&2
|
||||
echo "$0: check lockdir '$lockdir'" >&2
|
||||
exit 1
|
||||
fi
|
||||
|
||||
if test $stat -ne 0; then
|
||||
rm -f "$tmpdepfile"
|
||||
exit $stat
|
||||
fi
|
||||
rm -f "$depfile"
|
||||
# Each line is of the form `foo.o: dependent.h',
|
||||
# or `foo.o: dep1.h dep2.h \', or ` dep3.h dep4.h \'.
|
||||
# Do two passes, one to just change these to
|
||||
# `$object: dependent.h' and one to simply `dependent.h:'.
|
||||
sed "s,^[^:]*:,$object :," < "$tmpdepfile" > "$depfile"
|
||||
# Some versions of the HPUX 10.20 sed can't process this invocation
|
||||
# correctly. Breaking it into two sed invocations is a workaround.
|
||||
sed 's,^[^:]*: \(.*\)$,\1,;s/^\\$//;/^$/d;/:$/d' < "$tmpdepfile" \
|
||||
| sed -e 's/$/ :/' >> "$depfile"
|
||||
rm -f "$tmpdepfile"
|
||||
;;
|
||||
|
||||
hp2)
|
||||
# The "hp" stanza above does not work with aCC (C++) and HP's ia64
|
||||
# compilers, which have integrated preprocessors. The correct option
|
||||
# to use with these is +Maked; it writes dependencies to a file named
|
||||
# 'foo.d', which lands next to the object file, wherever that
|
||||
# happens to be.
|
||||
# Much of this is similar to the tru64 case; see comments there.
|
||||
set_dir_from "$object"
|
||||
set_base_from "$object"
|
||||
if test "$libtool" = yes; then
|
||||
tmpdepfile1=$dir$base.d
|
||||
tmpdepfile2=$dir.libs/$base.d
|
||||
"$@" -Wc,+Maked
|
||||
else
|
||||
tmpdepfile1=$dir$base.d
|
||||
tmpdepfile2=$dir$base.d
|
||||
"$@" +Maked
|
||||
fi
|
||||
stat=$?
|
||||
if test $stat -ne 0; then
|
||||
rm -f "$tmpdepfile1" "$tmpdepfile2"
|
||||
exit $stat
|
||||
fi
|
||||
|
||||
for tmpdepfile in "$tmpdepfile1" "$tmpdepfile2"
|
||||
do
|
||||
test -f "$tmpdepfile" && break
|
||||
done
|
||||
if test -f "$tmpdepfile"; then
|
||||
sed -e "s,^.*\.[$lower]*:,$object:," "$tmpdepfile" > "$depfile"
|
||||
# Add 'dependent.h:' lines.
|
||||
sed -ne '2,${
|
||||
s/^ *//
|
||||
s/ \\*$//
|
||||
s/$/:/
|
||||
p
|
||||
}' "$tmpdepfile" >> "$depfile"
|
||||
else
|
||||
make_dummy_depfile
|
||||
fi
|
||||
rm -f "$tmpdepfile" "$tmpdepfile2"
|
||||
;;
|
||||
|
||||
tru64)
|
||||
# The Tru64 compiler uses -MD to generate dependencies as a side
|
||||
# effect. 'cc -MD -o foo.o ...' puts the dependencies into 'foo.o.d'.
|
||||
# At least on Alpha/Redhat 6.1, Compaq CCC V6.2-504 seems to put
|
||||
# dependencies in 'foo.d' instead, so we check for that too.
|
||||
# Subdirectories are respected.
|
||||
set_dir_from "$object"
|
||||
set_base_from "$object"
|
||||
|
||||
if test "$libtool" = yes; then
|
||||
# Libtool generates 2 separate objects for the 2 libraries. These
|
||||
# two compilations output dependencies in $dir.libs/$base.o.d and
|
||||
# in $dir$base.o.d. We have to check for both files, because
|
||||
# one of the two compilations can be disabled. We should prefer
|
||||
# $dir$base.o.d over $dir.libs/$base.o.d because the latter is
|
||||
# automatically cleaned when .libs/ is deleted, while ignoring
|
||||
# the former would cause a distcleancheck panic.
|
||||
tmpdepfile1=$dir$base.o.d # libtool 1.5
|
||||
tmpdepfile2=$dir.libs/$base.o.d # Likewise.
|
||||
tmpdepfile3=$dir.libs/$base.d # Compaq CCC V6.2-504
|
||||
"$@" -Wc,-MD
|
||||
else
|
||||
tmpdepfile1=$dir$base.d
|
||||
tmpdepfile2=$dir$base.d
|
||||
tmpdepfile3=$dir$base.d
|
||||
"$@" -MD
|
||||
fi
|
||||
|
||||
stat=$?
|
||||
if test $stat -ne 0; then
|
||||
rm -f "$tmpdepfile1" "$tmpdepfile2" "$tmpdepfile3"
|
||||
exit $stat
|
||||
fi
|
||||
|
||||
for tmpdepfile in "$tmpdepfile1" "$tmpdepfile2" "$tmpdepfile3"
|
||||
do
|
||||
test -f "$tmpdepfile" && break
|
||||
done
|
||||
# Same post-processing that is required for AIX mode.
|
||||
aix_post_process_depfile
|
||||
;;
|
||||
|
||||
msvc7)
|
||||
if test "$libtool" = yes; then
|
||||
showIncludes=-Wc,-showIncludes
|
||||
else
|
||||
showIncludes=-showIncludes
|
||||
fi
|
||||
"$@" $showIncludes > "$tmpdepfile"
|
||||
stat=$?
|
||||
grep -v '^Note: including file: ' "$tmpdepfile"
|
||||
if test $stat -ne 0; then
|
||||
rm -f "$tmpdepfile"
|
||||
exit $stat
|
||||
fi
|
||||
rm -f "$depfile"
|
||||
echo "$object : \\" > "$depfile"
|
||||
# The first sed program below extracts the file names and escapes
|
||||
# backslashes for cygpath. The second sed program outputs the file
|
||||
# name when reading, but also accumulates all include files in the
|
||||
# hold buffer in order to output them again at the end. This only
|
||||
# works with sed implementations that can handle large buffers.
|
||||
sed < "$tmpdepfile" -n '
|
||||
/^Note: including file: *\(.*\)/ {
|
||||
s//\1/
|
||||
s/\\/\\\\/g
|
||||
p
|
||||
}' | $cygpath_u | sort -u | sed -n '
|
||||
s/ /\\ /g
|
||||
s/\(.*\)/'"$tab"'\1 \\/p
|
||||
s/.\(.*\) \\/\1:/
|
||||
H
|
||||
$ {
|
||||
s/.*/'"$tab"'/
|
||||
G
|
||||
p
|
||||
}' >> "$depfile"
|
||||
echo >> "$depfile" # make sure the fragment doesn't end with a backslash
|
||||
rm -f "$tmpdepfile"
|
||||
;;
|
||||
|
||||
msvc7msys)
|
||||
# This case exists only to let depend.m4 do its work. It works by
|
||||
# looking at the text of this script. This case will never be run,
|
||||
# since it is checked for above.
|
||||
exit 1
|
||||
;;
|
||||
|
||||
#nosideeffect)
|
||||
# This comment above is used by automake to tell side-effect
|
||||
# dependency tracking mechanisms from slower ones.
|
||||
|
||||
dashmstdout)
|
||||
# Important note: in order to support this mode, a compiler *must*
|
||||
# always write the preprocessed file to stdout, regardless of -o.
|
||||
"$@" || exit $?
|
||||
|
||||
# Remove the call to Libtool.
|
||||
if test "$libtool" = yes; then
|
||||
while test "X$1" != 'X--mode=compile'; do
|
||||
shift
|
||||
done
|
||||
shift
|
||||
fi
|
||||
|
||||
# Remove '-o $object'.
|
||||
IFS=" "
|
||||
for arg
|
||||
do
|
||||
case $arg in
|
||||
-o)
|
||||
shift
|
||||
;;
|
||||
$object)
|
||||
shift
|
||||
;;
|
||||
*)
|
||||
set fnord "$@" "$arg"
|
||||
shift # fnord
|
||||
shift # $arg
|
||||
;;
|
||||
esac
|
||||
done
|
||||
|
||||
test -z "$dashmflag" && dashmflag=-M
|
||||
# Require at least two characters before searching for ':'
|
||||
# in the target name. This is to cope with DOS-style filenames:
|
||||
# a dependency such as 'c:/foo/bar' could be seen as target 'c' otherwise.
|
||||
"$@" $dashmflag |
|
||||
sed "s|^[$tab ]*[^:$tab ][^:][^:]*:[$tab ]*|$object: |" > "$tmpdepfile"
|
||||
rm -f "$depfile"
|
||||
cat < "$tmpdepfile" > "$depfile"
|
||||
# Some versions of the HPUX 10.20 sed can't process this sed invocation
|
||||
# correctly. Breaking it into two sed invocations is a workaround.
|
||||
tr ' ' "$nl" < "$tmpdepfile" \
|
||||
| sed -e 's/^\\$//' -e '/^$/d' -e '/:$/d' \
|
||||
| sed -e 's/$/ :/' >> "$depfile"
|
||||
rm -f "$tmpdepfile"
|
||||
;;
|
||||
|
||||
dashXmstdout)
|
||||
# This case only exists to satisfy depend.m4. It is never actually
|
||||
# run, as this mode is specially recognized in the preamble.
|
||||
exit 1
|
||||
;;
|
||||
|
||||
makedepend)
|
||||
"$@" || exit $?
|
||||
# Remove any Libtool call
|
||||
if test "$libtool" = yes; then
|
||||
while test "X$1" != 'X--mode=compile'; do
|
||||
shift
|
||||
done
|
||||
shift
|
||||
fi
|
||||
# X makedepend
|
||||
shift
|
||||
cleared=no eat=no
|
||||
for arg
|
||||
do
|
||||
case $cleared in
|
||||
no)
|
||||
set ""; shift
|
||||
cleared=yes ;;
|
||||
esac
|
||||
if test $eat = yes; then
|
||||
eat=no
|
||||
continue
|
||||
fi
|
||||
case "$arg" in
|
||||
-D*|-I*)
|
||||
set fnord "$@" "$arg"; shift ;;
|
||||
# Strip any option that makedepend may not understand. Remove
|
||||
# the object too, otherwise makedepend will parse it as a source file.
|
||||
-arch)
|
||||
eat=yes ;;
|
||||
-*|$object)
|
||||
;;
|
||||
*)
|
||||
set fnord "$@" "$arg"; shift ;;
|
||||
esac
|
||||
done
|
||||
obj_suffix=`echo "$object" | sed 's/^.*\././'`
|
||||
touch "$tmpdepfile"
|
||||
${MAKEDEPEND-makedepend} -o"$obj_suffix" -f"$tmpdepfile" "$@"
|
||||
rm -f "$depfile"
|
||||
# makedepend may prepend the VPATH from the source file name to the object.
|
||||
# No need to regex-escape $object, excess matching of '.' is harmless.
|
||||
sed "s|^.*\($object *:\)|\1|" "$tmpdepfile" > "$depfile"
|
||||
# Some versions of the HPUX 10.20 sed can't process the last invocation
|
||||
# correctly. Breaking it into two sed invocations is a workaround.
|
||||
sed '1,2d' "$tmpdepfile" \
|
||||
| tr ' ' "$nl" \
|
||||
| sed -e 's/^\\$//' -e '/^$/d' -e '/:$/d' \
|
||||
| sed -e 's/$/ :/' >> "$depfile"
|
||||
rm -f "$tmpdepfile" "$tmpdepfile".bak
|
||||
;;
|
||||
|
||||
cpp)
|
||||
# Important note: in order to support this mode, a compiler *must*
|
||||
# always write the preprocessed file to stdout.
|
||||
"$@" || exit $?
|
||||
|
||||
# Remove the call to Libtool.
|
||||
if test "$libtool" = yes; then
|
||||
while test "X$1" != 'X--mode=compile'; do
|
||||
shift
|
||||
done
|
||||
shift
|
||||
fi
|
||||
|
||||
# Remove '-o $object'.
|
||||
IFS=" "
|
||||
for arg
|
||||
do
|
||||
case $arg in
|
||||
-o)
|
||||
shift
|
||||
;;
|
||||
$object)
|
||||
shift
|
||||
;;
|
||||
*)
|
||||
set fnord "$@" "$arg"
|
||||
shift # fnord
|
||||
shift # $arg
|
||||
;;
|
||||
esac
|
||||
done
|
||||
|
||||
"$@" -E \
|
||||
| sed -n -e '/^# [0-9][0-9]* "\([^"]*\)".*/ s:: \1 \\:p' \
|
||||
-e '/^#line [0-9][0-9]* "\([^"]*\)".*/ s:: \1 \\:p' \
|
||||
| sed '$ s: \\$::' > "$tmpdepfile"
|
||||
rm -f "$depfile"
|
||||
echo "$object : \\" > "$depfile"
|
||||
cat < "$tmpdepfile" >> "$depfile"
|
||||
sed < "$tmpdepfile" '/^$/d;s/^ //;s/ \\$//;s/$/ :/' >> "$depfile"
|
||||
rm -f "$tmpdepfile"
|
||||
;;
|
||||
|
||||
msvisualcpp)
|
||||
# Important note: in order to support this mode, a compiler *must*
|
||||
# always write the preprocessed file to stdout.
|
||||
"$@" || exit $?
|
||||
|
||||
# Remove the call to Libtool.
|
||||
if test "$libtool" = yes; then
|
||||
while test "X$1" != 'X--mode=compile'; do
|
||||
shift
|
||||
done
|
||||
shift
|
||||
fi
|
||||
|
||||
IFS=" "
|
||||
for arg
|
||||
do
|
||||
case "$arg" in
|
||||
-o)
|
||||
shift
|
||||
;;
|
||||
$object)
|
||||
shift
|
||||
;;
|
||||
"-Gm"|"/Gm"|"-Gi"|"/Gi"|"-ZI"|"/ZI")
|
||||
set fnord "$@"
|
||||
shift
|
||||
shift
|
||||
;;
|
||||
*)
|
||||
set fnord "$@" "$arg"
|
||||
shift
|
||||
shift
|
||||
;;
|
||||
esac
|
||||
done
|
||||
"$@" -E 2>/dev/null |
|
||||
sed -n '/^#line [0-9][0-9]* "\([^"]*\)"/ s::\1:p' | $cygpath_u | sort -u > "$tmpdepfile"
|
||||
rm -f "$depfile"
|
||||
echo "$object : \\" > "$depfile"
|
||||
sed < "$tmpdepfile" -n -e 's% %\\ %g' -e '/^\(.*\)$/ s::'"$tab"'\1 \\:p' >> "$depfile"
|
||||
echo "$tab" >> "$depfile"
|
||||
sed < "$tmpdepfile" -n -e 's% %\\ %g' -e '/^\(.*\)$/ s::\1\::p' >> "$depfile"
|
||||
rm -f "$tmpdepfile"
|
||||
;;
|
||||
|
||||
msvcmsys)
|
||||
# This case exists only to let depend.m4 do its work. It works by
|
||||
# looking at the text of this script. This case will never be run,
|
||||
# since it is checked for above.
|
||||
exit 1
|
||||
;;
|
||||
|
||||
none)
|
||||
exec "$@"
|
||||
;;
|
||||
|
||||
*)
|
||||
echo "Unknown depmode $depmode" 1>&2
|
||||
exit 1
|
||||
;;
|
||||
esac
|
||||
|
||||
exit 0
|
||||
|
||||
# Local Variables:
|
||||
# mode: shell-script
|
||||
# sh-indentation: 2
|
||||
# eval: (add-hook 'before-save-hook 'time-stamp)
|
||||
# time-stamp-start: "scriptversion="
|
||||
# time-stamp-format: "%:y-%02m-%02d.%02H"
|
||||
# time-stamp-time-zone: "UTC0"
|
||||
# time-stamp-end: "; # UTC"
|
||||
# End:
|
264
trunk/3rdparty/gperftools-2-fit/docs/cpuprofile-fileformat.html
vendored
Normal file
|
@ -0,0 +1,264 @@
|
|||
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
|
||||
<HTML>
|
||||
|
||||
<HEAD>
|
||||
<link rel="stylesheet" href="designstyle.css">
|
||||
<title>Google CPU Profiler Binary Data File Format</title>
|
||||
</HEAD>
|
||||
|
||||
<BODY>
|
||||
|
||||
<h1>Google CPU Profiler Binary Data File Format</h1>
|
||||
|
||||
<p align=right>
|
||||
<i>Last modified
|
||||
<script type=text/javascript>
|
||||
var lm = new Date(document.lastModified);
|
||||
document.write(lm.toDateString());
|
||||
</script></i>
|
||||
</p>
|
||||
|
||||
<p>This file documents the binary data file format produced by the
|
||||
Google CPU Profiler. For information about using the CPU Profiler,
|
||||
see <a href="cpuprofile.html">its user guide</a>.
|
||||
|
||||
<p>The profiler source code, which generates files using this format, is at
|
||||
<code>src/profiler.cc</code></a>.
|
||||
|
||||
|
||||
<h2>CPU Profile Data File Structure</h2>
|
||||
|
||||
<p>CPU profile data files each consist of four parts, in order:
|
||||
|
||||
<ul>
|
||||
<li> Binary header
|
||||
<li> Binary profile records
|
||||
<li> Binary trailer
|
||||
<li> Text list of mapped objects
|
||||
</ul>
|
||||
|
||||
<p>The binary data is expressed in terms of "slots." These are words
|
||||
large enough to hold the program's pointer type, i.e., for 32-bit
|
||||
programs they are 4 bytes in size, and for 64-bit programs they are 8
|
||||
bytes. They are stored in the profile data file in the native byte
|
||||
order (i.e., little-endian for x86 and x86_64).
|
||||
|
||||
|
||||
<h2>Binary Header</h2>
|
||||
|
||||
<p>The binary header format is show below. Values written by the
|
||||
profiler, along with requirements currently enforced by the analysis
|
||||
tools, are shown in parentheses.
|
||||
|
||||
<p>
|
||||
<table summary="Header Format"
|
||||
frame="box" rules="sides" cellpadding="5" width="50%">
|
||||
<tr>
|
||||
<th width="30%">slot</th>
|
||||
<th width="70%">data</th>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>0</td>
|
||||
<td>header count (0; must be 0)</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>1</td>
|
||||
<td>header slots after this one (3; must be >= 3)</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>2</td>
|
||||
<td>format version (0; must be 0)</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>3</td>
|
||||
<td>sampling period, in microseconds</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>4</td>
|
||||
<td>padding (0)</td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
<p>The headers currently generated for 32-bit and 64-bit little-endian
|
||||
(x86 and x86_64) profiles are shown below, for comparison.
|
||||
|
||||
<p>
|
||||
<table summary="Header Example" frame="box" rules="sides" cellpadding="5">
|
||||
<tr>
|
||||
<th></th>
|
||||
<th>hdr count</th>
|
||||
<th>hdr words</th>
|
||||
<th>version</th>
|
||||
<th>sampling period</th>
|
||||
<th>pad</th>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>32-bit or 64-bit (slots)</td>
|
||||
<td>0</td>
|
||||
<td>3</td>
|
||||
<td>0</td>
|
||||
<td>10000</td>
|
||||
<td>0</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>32-bit (4-byte words in file)</td>
|
||||
<td><tt>0x00000</tt></td>
|
||||
<td><tt>0x00003</tt></td>
|
||||
<td><tt>0x00000</tt></td>
|
||||
<td><tt>0x02710</tt></td>
|
||||
<td><tt>0x00000</tt></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>64-bit LE (4-byte words in file)</td>
|
||||
<td><tt>0x00000 0x00000</tt></td>
|
||||
<td><tt>0x00003 0x00000</tt></td>
|
||||
<td><tt>0x00000 0x00000</tt></td>
|
||||
<td><tt>0x02710 0x00000</tt></td>
|
||||
<td><tt>0x00000 0x00000</tt></td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
<p>The contents are shown in terms of slots, and in terms of 4-byte
|
||||
words in the profile data file. The slot contents for 32-bit and
|
||||
64-bit headers are identical. For 32-bit profiles, the 4-byte word
|
||||
view matches the slot view. For 64-bit profiles, each (8-byte) slot
|
||||
is shown as two 4-byte words, ordered as they would appear in the
|
||||
file.
|
||||
|
||||
<p>The profiling tools examine the contents of the file and use the
|
||||
expected locations and values of the header words field to detect
|
||||
whether the file is 32-bit or 64-bit.
|
||||
|
||||
|
||||
<h2>Binary Profile Records</h2>
|
||||
|
||||
<p>The binary profile record format is shown below.
|
||||
|
||||
<p>
|
||||
<table summary="Profile Record Format"
|
||||
frame="box" rules="sides" cellpadding="5" width="50%">
|
||||
<tr>
|
||||
<th width="30%">slot</th>
|
||||
<th width="70%">data</th>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>0</td>
|
||||
<td>sample count, must be >= 1</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>1</td>
|
||||
<td>number of call chain PCs (num_pcs), must be >= 1</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>2 .. (num_pcs + 1)</td>
|
||||
<td>call chain PCs, most-recently-called function first.
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
<p>The total length of a given record is 2 + num_pcs.
|
||||
|
||||
<p>Note that multiple profile records can be emitted by the profiler
|
||||
having an identical call chain. In that case, analysis tools should
|
||||
sum the counts of all records having identical call chains.
|
||||
|
||||
<p><b>Note:</b> Some profile analysis tools terminate if they see
|
||||
<em>any</em> profile record with a call chain with its first entry
|
||||
having the address 0. (This is similar to the binary trailer.)
|
||||
|
||||
<h3>Example</h3>
|
||||
|
||||
This example shows the slots contained in a sample profile record.
|
||||
|
||||
<p>
|
||||
<table summary="Profile Record Example"
|
||||
frame="box" rules="sides" cellpadding="5">
|
||||
<tr>
|
||||
<td>5</td>
|
||||
<td>3</td>
|
||||
<td>0xa0000</td>
|
||||
<td>0xc0000</td>
|
||||
<td>0xe0000</td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
<p>In this example, 5 ticks were received at PC 0xa0000, whose
|
||||
function had been called by the function containing 0xc0000, which had
|
||||
been called from the function containing 0xe0000.
|
||||
|
||||
|
||||
<h2>Binary Trailer</h2>
|
||||
|
||||
<p>The binary trailer consists of three slots of data with fixed
|
||||
values, shown below.
|
||||
|
||||
<p>
|
||||
<table summary="Trailer Format"
|
||||
frame="box" rules="sides" cellpadding="5" width="50%">
|
||||
<tr>
|
||||
<th width="30%">slot</th>
|
||||
<th width="70%">value</th>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>0</td>
|
||||
<td>0</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>1</td>
|
||||
<td>1</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>2</td>
|
||||
<td>0</td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
<p>Note that this is the same data that would contained in a profile
|
||||
record with sample count = 0, num_pcs = 1, and a one-element call
|
||||
chain containing the address 0.
|
||||
|
||||
|
||||
<h2>Text List of Mapped Objects</h2>
|
||||
|
||||
<p>The binary data in the file is followed immediately by a list of
|
||||
mapped objects. This list consists of lines of text separated by
|
||||
newline characters.
|
||||
|
||||
<p>Each line is one of the following types:
|
||||
|
||||
<ul>
|
||||
<li>Build specifier, starting with "<tt>build=</tt>". For example:
|
||||
<pre> build=/path/to/binary</pre>
|
||||
Leading spaces on the line are ignored.
|
||||
|
||||
<li>Mapping line from ProcMapsIterator::FormatLine. For example:
|
||||
<pre> 40000000-40015000 r-xp 00000000 03:01 12845071 /lib/ld-2.3.2.so</pre>
|
||||
The first address must start at the beginning of the line.
|
||||
</ul>
|
||||
|
||||
<p>Unrecognized lines should be ignored by analysis tools.
|
||||
|
||||
<p>When processing the paths see in mapping lines, occurrences of
|
||||
<tt>$build</tt> followed by a non-word character (i.e., characters
|
||||
other than underscore or alphanumeric characters), should be replaced
|
||||
by the path given on the last build specifier line.
|
||||
|
||||
<hr>
|
||||
<address>Chris Demetriou<br>
|
||||
<!-- Created: Mon Aug 27 12:18:26 PDT 2007 -->
|
||||
<!-- hhmts start -->
|
||||
Last modified: Mon Aug 27 12:18:26 PDT 2007 (cgd)
|
||||
<!-- hhmts end -->
|
||||
</address>
|
||||
</BODY>
|
||||
</HTML>
|
536
trunk/3rdparty/gperftools-2-fit/docs/cpuprofile.html
vendored
Normal file
|
@ -0,0 +1,536 @@
|
|||
<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML//EN">
|
||||
<HTML>
|
||||
|
||||
<HEAD>
|
||||
<link rel="stylesheet" href="designstyle.css">
|
||||
<title>Gperftools CPU Profiler</title>
|
||||
</HEAD>
|
||||
|
||||
<BODY>
|
||||
|
||||
<p align=right>
|
||||
<i>Last modified
|
||||
<script type=text/javascript>
|
||||
var lm = new Date(document.lastModified);
|
||||
document.write(lm.toDateString());
|
||||
</script></i>
|
||||
</p>
|
||||
|
||||
<p>This is the CPU profiler we use at Google. There are three parts
|
||||
to using it: linking the library into an application, running the
|
||||
code, and analyzing the output.</p>
|
||||
|
||||
<p>On the off-chance that you should need to understand it, the CPU
|
||||
profiler data file format is documented separately,
|
||||
<a href="cpuprofile-fileformat.html">here</a>.
|
||||
|
||||
|
||||
<H1>Linking in the Library</H1>
|
||||
|
||||
<p>To install the CPU profiler into your executable, add
|
||||
<code>-lprofiler</code> to the link-time step for your executable.
|
||||
(It's also probably possible to add in the profiler at run-time using
|
||||
<code>LD_PRELOAD</code>, e.g.
|
||||
<code>% env LD_PRELOAD="/usr/lib/libprofiler.so" <binary></code>,
|
||||
but this isn't necessarily recommended.)</p>
|
||||
|
||||
<p>This does <i>not</i> turn on CPU profiling; it just inserts the
|
||||
code. For that reason, it's practical to just always link
|
||||
<code>-lprofiler</code> into a binary while developing; that's what we
|
||||
do at Google. (However, since any user can turn on the profiler by
|
||||
setting an environment variable, it's not necessarily recommended to
|
||||
install profiler-linked binaries into a production, running
|
||||
system.)</p>
|
||||
|
||||
|
||||
<H1>Running the Code</H1>
|
||||
|
||||
<p>There are several alternatives to actually turn on CPU profiling
|
||||
for a given run of an executable:</p>
|
||||
|
||||
<ol>
|
||||
<li> <p>Define the environment variable CPUPROFILE to the filename
|
||||
to dump the profile to. For instance, if you had a version of
|
||||
<code>/bin/ls</code> that had been linked against libprofiler,
|
||||
you could run:</p>
|
||||
<pre>% env CPUPROFILE=ls.prof /bin/ls</pre>
|
||||
</li>
|
||||
<li> <p>In addition to defining the environment variable CPUPROFILE
|
||||
you can also define CPUPROFILESIGNAL. This allows profiling to be
|
||||
controlled via the signal number that you specify. The signal number
|
||||
must be unused by the program under normal operation. Internally it
|
||||
acts as a switch, triggered by the signal, which is off by default.
|
||||
For instance, if you had a copy of <code>/bin/chrome</code> that had been
|
||||
been linked against libprofiler, you could run:</p>
|
||||
<pre>% env CPUPROFILE=chrome.prof CPUPROFILESIGNAL=12 /bin/chrome &</pre>
|
||||
<p>You can then trigger profiling to start:</p>
|
||||
<pre>% killall -12 chrome</pre>
|
||||
<p>Then after a period of time you can tell it to stop which will
|
||||
generate the profile:</p>
|
||||
<pre>% killall -12 chrome</pre>
|
||||
</li>
|
||||
<li> <p>In your code, bracket the code you want profiled in calls to
|
||||
<code>ProfilerStart()</code> and <code>ProfilerStop()</code>.
|
||||
(These functions are declared in <code><gperftools/profiler.h></code>.)
|
||||
<code>ProfilerStart()</code> will take
|
||||
the profile-filename as an argument.</p>
|
||||
</li>
|
||||
</ol>
|
||||
|
||||
<p>In Linux 2.6 and above, profiling works correctly with threads,
|
||||
automatically profiling all threads. In Linux 2.4, profiling only
|
||||
profiles the main thread (due to a kernel bug involving itimers and
|
||||
threads). Profiling works correctly with sub-processes: each child
|
||||
process gets its own profile with its own name (generated by combining
|
||||
CPUPROFILE with the child's process id).</p>
|
||||
|
||||
<p>For security reasons, CPU profiling will not write to a file -- and
|
||||
is thus not usable -- for setuid programs.</p>
|
||||
|
||||
<p>See the include-file <code>gperftools/profiler.h</code> for
|
||||
advanced-use functions, including <code>ProfilerFlush()</code> and
|
||||
<code>ProfilerStartWithOptions()</code>.</p>
|
||||
|
||||
|
||||
<H2>Modifying Runtime Behavior</H2>
|
||||
|
||||
<p>You can more finely control the behavior of the CPU profiler via
|
||||
environment variables.</p>
|
||||
|
||||
<table frame=box rules=sides cellpadding=5 width=100%>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>CPUPROFILE_FREQUENCY=<i>x</i></code></td>
|
||||
<td>default: 100</td>
|
||||
<td>
|
||||
How many interrupts/second the cpu-profiler samples.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>CPUPROFILE_REALTIME=1</code></td>
|
||||
<td>default: [not set]</td>
|
||||
<td>
|
||||
If set to any value (including 0 or the empty string), use
|
||||
ITIMER_REAL instead of ITIMER_PROF to gather profiles. In
|
||||
general, ITIMER_REAL is not as accurate as ITIMER_PROF, and also
|
||||
interacts badly with use of alarm(), so prefer ITIMER_PROF unless
|
||||
you have a reason prefer ITIMER_REAL.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
</table>
|
||||
|
||||
|
||||
<h1><a name="pprof">Analyzing the Output</a></h1>
|
||||
|
||||
<p><code>pprof</code> is the script used to analyze a profile. It has
|
||||
many output modes, both textual and graphical. Some give just raw
|
||||
numbers, much like the <code>-pg</code> output of <code>gcc</code>,
|
||||
and others show the data in the form of a dependency graph.</p>
|
||||
|
||||
<p>pprof <b>requires</b> <code>perl5</code> to be installed to run.
|
||||
It also requires <code>dot</code> to be installed for any of the
|
||||
graphical output routines, and <code>gv</code> to be installed for
|
||||
<code>--gv</code> mode (described below).
|
||||
</p>
|
||||
|
||||
<p>Here are some ways to call pprof. These are described in more
|
||||
detail below.</p>
|
||||
|
||||
<pre>
|
||||
% pprof /bin/ls ls.prof
|
||||
Enters "interactive" mode
|
||||
% pprof --text /bin/ls ls.prof
|
||||
Outputs one line per procedure
|
||||
% pprof --gv /bin/ls ls.prof
|
||||
Displays annotated call-graph via 'gv'
|
||||
% pprof --gv --focus=Mutex /bin/ls ls.prof
|
||||
Restricts to code paths including a .*Mutex.* entry
|
||||
% pprof --gv --focus=Mutex --ignore=string /bin/ls ls.prof
|
||||
Code paths including Mutex but not string
|
||||
% pprof --list=getdir /bin/ls ls.prof
|
||||
(Per-line) annotated source listing for getdir()
|
||||
% pprof --disasm=getdir /bin/ls ls.prof
|
||||
(Per-PC) annotated disassembly for getdir()
|
||||
% pprof --text localhost:1234
|
||||
Outputs one line per procedure for localhost:1234
|
||||
% pprof --callgrind /bin/ls ls.prof
|
||||
Outputs the call information in callgrind format
|
||||
</pre>
|
||||
|
||||
|
||||
<h3>Analyzing Text Output</h3>
|
||||
|
||||
<p>Text mode has lines of output that look like this:</p>
|
||||
<pre>
|
||||
14 2.1% 17.2% 58 8.7% std::_Rb_tree::find
|
||||
</pre>
|
||||
|
||||
<p>Here is how to interpret the columns:</p>
|
||||
<ol>
|
||||
<li> Number of profiling samples in this function
|
||||
<li> Percentage of profiling samples in this function
|
||||
<li> Percentage of profiling samples in the functions printed so far
|
||||
<li> Number of profiling samples in this function and its callees
|
||||
<li> Percentage of profiling samples in this function and its callees
|
||||
<li> Function name
|
||||
</ol>
|
||||
|
||||
<h3>Analyzing Callgrind Output</h3>
|
||||
|
||||
<p>Use <a href="http://kcachegrind.sourceforge.net">kcachegrind</a> to
|
||||
analyze your callgrind output:</p>
|
||||
<pre>
|
||||
% pprof --callgrind /bin/ls ls.prof > ls.callgrind
|
||||
% kcachegrind ls.callgrind
|
||||
</pre>
|
||||
|
||||
<p>The cost is specified in 'hits', i.e. how many times a function
|
||||
appears in the recorded call stack information. The 'calls' from
|
||||
function a to b record how many times function b was found in the
|
||||
stack traces directly below function a.</p>
|
||||
|
||||
<p>Tip: if you use a debug build the output will include file and line
|
||||
number information and kcachegrind will show an annotated source
|
||||
code view.</p>
|
||||
|
||||
<h3>Node Information</h3>
|
||||
|
||||
<p>In the various graphical modes of pprof, the output is a call graph
|
||||
annotated with timing information, like so:</p>
|
||||
|
||||
<A HREF="pprof-test-big.gif">
|
||||
<center><table><tr><td>
|
||||
<img src="pprof-test.gif">
|
||||
</td></tr></table></center>
|
||||
</A>
|
||||
|
||||
<p>Each node represents a procedure. The directed edges indicate
|
||||
caller to callee relations. Each node is formatted as follows:</p>
|
||||
|
||||
<center><pre>
|
||||
Class Name
|
||||
Method Name
|
||||
local (percentage)
|
||||
<b>of</b> cumulative (percentage)
|
||||
</pre></center>
|
||||
|
||||
<p>The last one or two lines contains the timing information. (The
|
||||
profiling is done via a sampling method, where by default we take 100
|
||||
samples a second. Therefor one unit of time in the output corresponds
|
||||
to about 10 milliseconds of execution time.) The "local" time is the
|
||||
time spent executing the instructions directly contained in the
|
||||
procedure (and in any other procedures that were inlined into the
|
||||
procedure). The "cumulative" time is the sum of the "local" time and
|
||||
the time spent in any callees. If the cumulative time is the same as
|
||||
the local time, it is not printed.</p>
|
||||
|
||||
<p>For instance, the timing information for test_main_thread()
|
||||
indicates that 155 units (about 1.55 seconds) were spent executing the
|
||||
code in <code>test_main_thread()</code> and 200 units were spent while
|
||||
executing <code>test_main_thread()</code> and its callees such as
|
||||
<code>snprintf()</code>.</p>
|
||||
|
||||
<p>The size of the node is proportional to the local count. The
|
||||
percentage displayed in the node corresponds to the count divided by
|
||||
the total run time of the program (that is, the cumulative count for
|
||||
<code>main()</code>).</p>
|
||||
|
||||
<h3>Edge Information</h3>
|
||||
|
||||
<p>An edge from one node to another indicates a caller to callee
|
||||
relationship. Each edge is labelled with the time spent by the callee
|
||||
on behalf of the caller. E.g, the edge from
|
||||
<code>test_main_thread()</code> to <code>snprintf()</code> indicates
|
||||
that of the 200 samples in <code>test_main_thread()</code>, 37 are
|
||||
because of calls to <code>snprintf()</code>.</p>
|
||||
|
||||
<p>Note that <code>test_main_thread()</code> has an edge to
|
||||
<code>vsnprintf()</code>, even though <code>test_main_thread()</code>
|
||||
doesn't call that function directly. This is because the code was
|
||||
compiled with <code>-O2</code>; the profile reflects the optimized
|
||||
control flow.</p>
|
||||
|
||||
<h3>Meta Information</h3>
|
||||
|
||||
<p>The top of the display should contain some meta information
|
||||
like:</p>
|
||||
<pre>
|
||||
/tmp/profiler2_unittest
|
||||
Total samples: 202
|
||||
Focusing on: 202
|
||||
Dropped nodes with <= 1 abs(samples)
|
||||
Dropped edges with <= 0 samples
|
||||
</pre>
|
||||
|
||||
<p>This section contains the name of the program, and the total
|
||||
samples collected during the profiling run. If the
|
||||
<code>--focus</code> option is on (see the <a href="#focus">Focus</a>
|
||||
section below), the legend also contains the number of samples being
|
||||
shown in the focused display. Furthermore, some unimportant nodes and
|
||||
edges are dropped to reduce clutter. The characteristics of the
|
||||
dropped nodes and edges are also displayed in the legend.</p>
|
||||
|
||||
<h3><a name=focus>Focus and Ignore</a></h3>
|
||||
|
||||
<p>You can ask pprof to generate a display focused on a particular
|
||||
piece of the program. You specify a regular expression. Any portion
|
||||
of the call-graph that is on a path which contains at least one node
|
||||
matching the regular expression is preserved. The rest of the
|
||||
call-graph is dropped on the floor. For example, you can focus on the
|
||||
<code>vsnprintf()</code> libc call in <code>profiler2_unittest</code>
|
||||
as follows:</p>
|
||||
|
||||
<pre>
|
||||
% pprof --gv --focus=vsnprintf /tmp/profiler2_unittest test.prof
|
||||
</pre>
|
||||
<A HREF="pprof-vsnprintf-big.gif">
|
||||
<center><table><tr><td>
|
||||
<img src="pprof-vsnprintf.gif">
|
||||
</td></tr></table></center>
|
||||
</A>
|
||||
|
||||
<p>Similarly, you can supply the <code>--ignore</code> option to
|
||||
ignore samples that match a specified regular expression. E.g., if
|
||||
you are interested in everything except calls to
|
||||
<code>snprintf()</code>, you can say:</p>
|
||||
<pre>
|
||||
% pprof --gv --ignore=snprintf /tmp/profiler2_unittest test.prof
|
||||
</pre>
|
||||
|
||||
|
||||
<h3>Interactive mode</a></h3>
|
||||
|
||||
<p>By default -- if you don't specify any flags to the contrary --
|
||||
pprof runs in interactive mode. At the <code>(pprof)</code> prompt,
|
||||
you can run many of the commands described above. You can type
|
||||
<code>help</code> for a list of what commands are available in
|
||||
interactive mode.</p>
|
||||
|
||||
<h3><a name=options>pprof Options</a></h3>
|
||||
|
||||
For a complete list of pprof options, you can run <code>pprof
|
||||
--help</code>.
|
||||
|
||||
<h4>Output Type</h4>
|
||||
|
||||
<p>
|
||||
<center>
|
||||
<table frame=box rules=sides cellpadding=5 width=100%>
|
||||
<tr valign=top>
|
||||
<td><code>--text</code></td>
|
||||
<td>
|
||||
Produces a textual listing. (Note: If you have an X display, and
|
||||
<code>dot</code> and <code>gv</code> installed, you will probably
|
||||
be happier with the <code>--gv</code> output.)
|
||||
</td>
|
||||
</tr>
|
||||
<tr valign=top>
|
||||
<td><code>--gv</code></td>
|
||||
<td>
|
||||
Generates annotated call-graph, converts to postscript, and
|
||||
displays via gv (requres <code>dot</code> and <code>gv</code> be
|
||||
installed).
|
||||
</td>
|
||||
</tr>
|
||||
<tr valign=top>
|
||||
<td><code>--dot</code></td>
|
||||
<td>
|
||||
Generates the annotated call-graph in dot format and
|
||||
emits to stdout (requres <code>dot</code> be installed).
|
||||
</td>
|
||||
</tr>
|
||||
<tr valign=top>
|
||||
<td><code>--ps</code></td>
|
||||
<td>
|
||||
Generates the annotated call-graph in Postscript format and
|
||||
emits to stdout (requres <code>dot</code> be installed).
|
||||
</td>
|
||||
</tr>
|
||||
<tr valign=top>
|
||||
<td><code>--pdf</code></td>
|
||||
<td>
|
||||
Generates the annotated call-graph in PDF format and emits to
|
||||
stdout (requires <code>dot</code> and <code>ps2pdf</code> be
|
||||
installed).
|
||||
</td>
|
||||
</tr>
|
||||
<tr valign=top>
|
||||
<td><code>--gif</code></td>
|
||||
<td>
|
||||
Generates the annotated call-graph in GIF format and
|
||||
emits to stdout (requres <code>dot</code> be installed).
|
||||
</td>
|
||||
</tr>
|
||||
<tr valign=top>
|
||||
<td><code>--list=<<i>regexp</i>></code></td>
|
||||
<td>
|
||||
<p>Outputs source-code listing of routines whose
|
||||
name matches <regexp>. Each line
|
||||
in the listing is annotated with flat and cumulative
|
||||
sample counts.</p>
|
||||
|
||||
<p>In the presence of inlined calls, the samples
|
||||
associated with inlined code tend to get assigned
|
||||
to a line that follows the location of the
|
||||
inlined call. A more precise accounting can be
|
||||
obtained by disassembling the routine using the
|
||||
--disasm flag.</p>
|
||||
</td>
|
||||
</tr>
|
||||
<tr valign=top>
|
||||
<td><code>--disasm=<<i>regexp</i>></code></td>
|
||||
<td>
|
||||
Generates disassembly of routines that match
|
||||
<regexp>, annotated with flat and
|
||||
cumulative sample counts and emits to stdout.
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</center>
|
||||
|
||||
<h4>Reporting Granularity</h4>
|
||||
|
||||
<p>By default, pprof produces one entry per procedure. However you can
|
||||
use one of the following options to change the granularity of the
|
||||
output. The <code>--files</code> option seems to be particularly
|
||||
useless, and may be removed eventually.</p>
|
||||
|
||||
<center>
|
||||
<table frame=box rules=sides cellpadding=5 width=100%>
|
||||
<tr valign=top>
|
||||
<td><code>--addresses</code></td>
|
||||
<td>
|
||||
Produce one node per program address.
|
||||
</td>
|
||||
</tr>
|
||||
<td><code>--lines</code></td>
|
||||
<td>
|
||||
Produce one node per source line.
|
||||
</td>
|
||||
</tr>
|
||||
<td><code>--functions</code></td>
|
||||
<td>
|
||||
Produce one node per function (this is the default).
|
||||
</td>
|
||||
</tr>
|
||||
<td><code>--files</code></td>
|
||||
<td>
|
||||
Produce one node per source file.
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</center>
|
||||
|
||||
<h4>Controlling the Call Graph Display</h4>
|
||||
|
||||
<p>Some nodes and edges are dropped to reduce clutter in the output
|
||||
display. The following options control this effect:</p>
|
||||
|
||||
<center>
|
||||
<table frame=box rules=sides cellpadding=5 width=100%>
|
||||
<tr valign=top>
|
||||
<td><code>--nodecount=<n></code></td>
|
||||
<td>
|
||||
This option controls the number of displayed nodes. The nodes
|
||||
are first sorted by decreasing cumulative count, and then only
|
||||
the top N nodes are kept. The default value is 80.
|
||||
</td>
|
||||
</tr>
|
||||
<tr valign=top>
|
||||
<td><code>--nodefraction=<f></code></td>
|
||||
<td>
|
||||
This option provides another mechanism for discarding nodes
|
||||
from the display. If the cumulative count for a node is
|
||||
less than this option's value multiplied by the total count
|
||||
for the profile, the node is dropped. The default value
|
||||
is 0.005; i.e. nodes that account for less than
|
||||
half a percent of the total time are dropped. A node
|
||||
is dropped if either this condition is satisfied, or the
|
||||
--nodecount condition is satisfied.
|
||||
</td>
|
||||
</tr>
|
||||
<tr valign=top>
|
||||
<td><code>--edgefraction=<f></code></td>
|
||||
<td>
|
||||
This option controls the number of displayed edges. First of all,
|
||||
an edge is dropped if either its source or destination node is
|
||||
dropped. Otherwise, the edge is dropped if the sample
|
||||
count along the edge is less than this option's value multiplied
|
||||
by the total count for the profile. The default value is
|
||||
0.001; i.e., edges that account for less than
|
||||
0.1% of the total time are dropped.
|
||||
</td>
|
||||
</tr>
|
||||
<tr valign=top>
|
||||
<td><code>--focus=<re></code></td>
|
||||
<td>
|
||||
This option controls what region of the graph is displayed
|
||||
based on the regular expression supplied with the option.
|
||||
For any path in the callgraph, we check all nodes in the path
|
||||
against the supplied regular expression. If none of the nodes
|
||||
match, the path is dropped from the output.
|
||||
</td>
|
||||
</tr>
|
||||
<tr valign=top>
|
||||
<td><code>--ignore=<re></code></td>
|
||||
<td>
|
||||
This option controls what region of the graph is displayed
|
||||
based on the regular expression supplied with the option.
|
||||
For any path in the callgraph, we check all nodes in the path
|
||||
against the supplied regular expression. If any of the nodes
|
||||
match, the path is dropped from the output.
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
</center>
|
||||
|
||||
<p>The dropped edges and nodes account for some count mismatches in
|
||||
the display. For example, the cumulative count for
|
||||
<code>snprintf()</code> in the first diagram above was 41. However
|
||||
the local count (1) and the count along the outgoing edges (12+1+20+6)
|
||||
add up to only 40.</p>
|
||||
|
||||
|
||||
<h1>Caveats</h1>
|
||||
|
||||
<ul>
|
||||
<li> If the program exits because of a signal, the generated profile
|
||||
will be <font color=red>incomplete, and may perhaps be
|
||||
completely empty</font>.
|
||||
<li> The displayed graph may have disconnected regions because
|
||||
of the edge-dropping heuristics described above.
|
||||
<li> If the program linked in a library that was not compiled
|
||||
with enough symbolic information, all samples associated
|
||||
with the library may be charged to the last symbol found
|
||||
in the program before the library. This will artificially
|
||||
inflate the count for that symbol.
|
||||
<li> If you run the program on one machine, and profile it on
|
||||
another, and the shared libraries are different on the two
|
||||
machines, the profiling output may be confusing: samples that
|
||||
fall within shared libaries may be assigned to arbitrary
|
||||
procedures.
|
||||
<li> If your program forks, the children will also be profiled
|
||||
(since they inherit the same CPUPROFILE setting). Each process
|
||||
is profiled separately; to distinguish the child profiles from
|
||||
the parent profile and from each other, all children will have
|
||||
their process-id appended to the CPUPROFILE name.
|
||||
<li> Due to a hack we make to work around a possible gcc bug, your
|
||||
profiles may end up named strangely if the first character of
|
||||
your CPUPROFILE variable has ascii value greater than 127.
|
||||
This should be exceedingly rare, but if you need to use such a
|
||||
name, just set prepend <code>./</code> to your filename:
|
||||
<code>CPUPROFILE=./Ägypten</code>.
|
||||
</ul>
|
||||
|
||||
|
||||
<hr>
|
||||
<address>Sanjay Ghemawat<br>
|
||||
<!-- Created: Tue Dec 19 10:43:14 PST 2000 -->
|
||||
<!-- hhmts start -->
|
||||
Last modified: Fri May 9 14:41:29 PDT 2008
|
||||
<!-- hhmts end -->
|
||||
</address>
|
||||
</BODY>
|
||||
</HTML>
|
109
trunk/3rdparty/gperftools-2-fit/docs/designstyle.css
vendored
Normal file
|
@ -0,0 +1,109 @@
|
|||
body {
|
||||
background-color: #ffffff;
|
||||
color: black;
|
||||
margin-right: 1in;
|
||||
margin-left: 1in;
|
||||
}
|
||||
|
||||
|
||||
h1, h2, h3, h4, h5, h6 {
|
||||
color: #3366ff;
|
||||
font-family: sans-serif;
|
||||
}
|
||||
@media print {
|
||||
/* Darker version for printing */
|
||||
h1, h2, h3, h4, h5, h6 {
|
||||
color: #000080;
|
||||
font-family: helvetica, sans-serif;
|
||||
}
|
||||
}
|
||||
|
||||
h1 {
|
||||
text-align: center;
|
||||
font-size: 18pt;
|
||||
}
|
||||
h2 {
|
||||
margin-left: -0.5in;
|
||||
}
|
||||
h3 {
|
||||
margin-left: -0.25in;
|
||||
}
|
||||
h4 {
|
||||
margin-left: -0.125in;
|
||||
}
|
||||
hr {
|
||||
margin-left: -1in;
|
||||
}
|
||||
|
||||
/* Definition lists: definition term bold */
|
||||
dt {
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
address {
|
||||
text-align: right;
|
||||
}
|
||||
/* Use the <code> tag for bits of code and <var> for variables and objects. */
|
||||
code,pre,samp,var {
|
||||
color: #006000;
|
||||
}
|
||||
/* Use the <file> tag for file and directory paths and names. */
|
||||
file {
|
||||
color: #905050;
|
||||
font-family: monospace;
|
||||
}
|
||||
/* Use the <kbd> tag for stuff the user should type. */
|
||||
kbd {
|
||||
color: #600000;
|
||||
}
|
||||
div.note p {
|
||||
float: right;
|
||||
width: 3in;
|
||||
margin-right: 0%;
|
||||
padding: 1px;
|
||||
border: 2px solid #6060a0;
|
||||
background-color: #fffff0;
|
||||
}
|
||||
|
||||
UL.nobullets {
|
||||
list-style-type: none;
|
||||
list-style-image: none;
|
||||
margin-left: -1em;
|
||||
}
|
||||
|
||||
/* pretty printing styles. See prettify.js */
|
||||
.str { color: #080; }
|
||||
.kwd { color: #008; }
|
||||
.com { color: #800; }
|
||||
.typ { color: #606; }
|
||||
.lit { color: #066; }
|
||||
.pun { color: #660; }
|
||||
.pln { color: #000; }
|
||||
.tag { color: #008; }
|
||||
.atn { color: #606; }
|
||||
.atv { color: #080; }
|
||||
pre.prettyprint { padding: 2px; border: 1px solid #888; }
|
||||
|
||||
.embsrc { background: #eee; }
|
||||
|
||||
@media print {
|
||||
.str { color: #060; }
|
||||
.kwd { color: #006; font-weight: bold; }
|
||||
.com { color: #600; font-style: italic; }
|
||||
.typ { color: #404; font-weight: bold; }
|
||||
.lit { color: #044; }
|
||||
.pun { color: #440; }
|
||||
.pln { color: #000; }
|
||||
.tag { color: #006; font-weight: bold; }
|
||||
.atn { color: #404; }
|
||||
.atv { color: #060; }
|
||||
}
|
||||
|
||||
/* Table Column Headers */
|
||||
.hdr {
|
||||
color: #006;
|
||||
font-weight: bold;
|
||||
background-color: #dddddd; }
|
||||
.hdr2 {
|
||||
color: #006;
|
||||
background-color: #eeeeee; }
|
BIN
trunk/3rdparty/gperftools-2-fit/docs/heap-example1.png
vendored
Normal file
After Width: | Height: | Size: 37 KiB |
534
trunk/3rdparty/gperftools-2-fit/docs/heap_checker.html
vendored
Normal file
|
@ -0,0 +1,534 @@
|
|||
<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML//EN">
|
||||
<HTML>
|
||||
|
||||
<HEAD>
|
||||
<link rel="stylesheet" href="designstyle.css">
|
||||
<title>Gperftools Heap Leak Checker</title>
|
||||
</HEAD>
|
||||
|
||||
<BODY>
|
||||
|
||||
<p align=right>
|
||||
<i>Last modified
|
||||
<script type=text/javascript>
|
||||
var lm = new Date(document.lastModified);
|
||||
document.write(lm.toDateString());
|
||||
</script></i>
|
||||
</p>
|
||||
|
||||
<p>This is the heap checker we use at Google to detect memory leaks in
|
||||
C++ programs. There are three parts to using it: linking the library
|
||||
into an application, running the code, and analyzing the output.</p>
|
||||
|
||||
|
||||
<H1>Linking in the Library</H1>
|
||||
|
||||
<p>The heap-checker is part of tcmalloc, so to install the heap
|
||||
checker into your executable, add <code>-ltcmalloc</code> to the
|
||||
link-time step for your executable. Also, while we don't necessarily
|
||||
recommend this form of usage, it's possible to add in the profiler at
|
||||
run-time using <code>LD_PRELOAD</code>:</p>
|
||||
<pre>% env LD_PRELOAD="/usr/lib/libtcmalloc.so" <binary></pre>
|
||||
|
||||
<p>This does <i>not</i> turn on heap checking; it just inserts the
|
||||
code. For that reason, it's practical to just always link
|
||||
<code>-ltcmalloc</code> into a binary while developing; that's what we
|
||||
do at Google. (However, since any user can turn on the profiler by
|
||||
setting an environment variable, it's not necessarily recommended to
|
||||
install heapchecker-linked binaries into a production, running
|
||||
system.) Note that if you wish to use the heap checker, you must
|
||||
also use the tcmalloc memory-allocation library. There is no way
|
||||
currently to use the heap checker separate from tcmalloc.</p>
|
||||
|
||||
|
||||
<h1>Running the Code</h1>
|
||||
|
||||
<p>Note: For security reasons, heap profiling will not write to a file
|
||||
-- and is thus not usable -- for setuid programs.</p>
|
||||
|
||||
<h2><a name="whole_program">Whole-program Heap Leak Checking</a></h2>
|
||||
|
||||
<p>The recommended way to use the heap checker is in "whole program"
|
||||
mode. In this case, the heap-checker starts tracking memory
|
||||
allocations before the start of <code>main()</code>, and checks again
|
||||
at program-exit. If it finds any memory leaks -- that is, any memory
|
||||
not pointed to by objects that are still "live" at program-exit -- it
|
||||
aborts the program (via <code>exit(1)</code>) and prints a message
|
||||
describing how to track down the memory leak (using <A
|
||||
HREF="heapprofile.html#pprof">pprof</A>).</p>
|
||||
|
||||
<p>The heap-checker records the stack trace for each allocation while
|
||||
it is active. This causes a significant increase in memory usage, in
|
||||
addition to slowing your program down.</p>
|
||||
|
||||
<p>Here's how to run a program with whole-program heap checking:</p>
|
||||
|
||||
<ol>
|
||||
<li> <p>Define the environment variable HEAPCHECK to the <A
|
||||
HREF="#types">type of heap-checking</A> to do. For instance,
|
||||
to heap-check
|
||||
<code>/usr/local/bin/my_binary_compiled_with_tcmalloc</code>:</p>
|
||||
<pre>% env HEAPCHECK=normal /usr/local/bin/my_binary_compiled_with_tcmalloc</pre>
|
||||
</ol>
|
||||
|
||||
<p>No other action is required.</p>
|
||||
|
||||
<p>Note that since the heap-checker uses the heap-profiling framework
|
||||
internally, it is not possible to run both the heap-checker and <A
|
||||
HREF="heapprofile.html">heap profiler</A> at the same time.</p>
|
||||
|
||||
|
||||
<h3><a name="types">Flavors of Heap Checking</a></h3>
|
||||
|
||||
<p>These are the legal values when running a whole-program heap
|
||||
check:</p>
|
||||
<ol>
|
||||
<li> <code>minimal</code>
|
||||
<li> <code>normal</code>
|
||||
<li> <code>strict</code>
|
||||
<li> <code>draconian</code>
|
||||
</ol>
|
||||
|
||||
<p>"Minimal" heap-checking starts as late as possible in a
|
||||
initialization, meaning you can leak some memory in your
|
||||
initialization routines (that run before <code>main()</code>, say),
|
||||
and not trigger a leak message. If you frequently (and purposefully)
|
||||
leak data in one-time global initializers, "minimal" mode is useful
|
||||
for you. Otherwise, you should avoid it for stricter modes.</p>
|
||||
|
||||
<p>"Normal" heap-checking tracks <A HREF="#live">live objects</A> and
|
||||
reports a leak for any data that is not reachable via a live object
|
||||
when the program exits.</p>
|
||||
|
||||
<p>"Strict" heap-checking is much like "normal" but has a few extra
|
||||
checks that memory isn't lost in global destructors. In particular,
|
||||
if you have a global variable that allocates memory during program
|
||||
execution, and then "forgets" about the memory in the global
|
||||
destructor (say, by setting the pointer to it to NULL) without freeing
|
||||
it, that will prompt a leak message in "strict" mode, though not in
|
||||
"normal" mode.</p>
|
||||
|
||||
<p>"Draconian" heap-checking is appropriate for those who like to be
|
||||
very precise about their memory management, and want the heap-checker
|
||||
to help them enforce it. In "draconian" mode, the heap-checker does
|
||||
not do "live object" checking at all, so it reports a leak unless
|
||||
<i>all</i> allocated memory is freed before program exit. (However,
|
||||
you can use <A HREF="#disable">IgnoreObject()</A> to re-enable
|
||||
liveness-checking on an object-by-object basis.)</p>
|
||||
|
||||
<p>"Normal" mode, as the name implies, is the one used most often at
|
||||
Google. It's appropriate for everyday heap-checking use.</p>
|
||||
|
||||
<p>In addition, there are two other possible modes:</p>
|
||||
<ul>
|
||||
<li> <code>as-is</code>
|
||||
<li> <code>local</code>
|
||||
</ul>
|
||||
<p><code>as-is</code> is the most flexible mode; it allows you to
|
||||
specify the various <A HREF="#options">knobs</A> of the heap checker
|
||||
explicitly. <code>local</code> activates the <A
|
||||
HREF="#explicit">explicit heap-check instrumentation</A>, but does not
|
||||
turn on any whole-program leak checking.</p>
|
||||
|
||||
|
||||
<h3><A NAME="tweaking">Tweaking whole-program checking</A></h3>
|
||||
|
||||
<p>In some cases you want to check the whole program for memory leaks,
|
||||
but waiting for after <code>main()</code> exits to do the first
|
||||
whole-program leak check is waiting too long: e.g. in a long-running
|
||||
server one might wish to simply periodically check for leaks while the
|
||||
server is running. In this case, you can call the static method
|
||||
<code>HeapLeakChecker::NoGlobalLeaks()</code>, to verify no global leaks have happened
|
||||
as of that point in the program.</p>
|
||||
|
||||
<p>Alternately, doing the check after <code>main()</code> exits might
|
||||
be too late. Perhaps you have some objects that are known not to
|
||||
clean up properly at exit. You'd like to do the "at exit" check
|
||||
before those objects are destroyed (since while they're live, any
|
||||
memory they point to will not be considered a leak). In that case,
|
||||
you can call <code>HeapLeakChecker::NoGlobalLeaks()</code> manually, near the end of
|
||||
<code>main()</code>, and then call <code>HeapLeakChecker::CancelGlobalCheck()</code> to
|
||||
turn off the automatic post-<code>main()</code> check.</p>
|
||||
|
||||
<p>Finally, there's a helper macro for "strict" and "draconian" modes,
|
||||
which require all global memory to be freed before program exit. This
|
||||
freeing can be time-consuming and is often unnecessary, since libc
|
||||
cleans up all memory at program-exit for you. If you want the
|
||||
benefits of "strict"/"draconian" modes without the cost of all that
|
||||
freeing, look at <code>REGISTER_HEAPCHECK_CLEANUP</code> (in
|
||||
<code>heap-checker.h</code>). This macro allows you to mark specific
|
||||
cleanup code as active only when the heap-checker is turned on.</p>
|
||||
|
||||
|
||||
<h2><a name="explicit">Explicit (Partial-program) Heap Leak Checking</h2>
|
||||
|
||||
<p>Instead of whole-program checking, you can check certain parts of your
|
||||
code to verify they do not have memory leaks. This check verifies that
|
||||
between two parts of a program, no memory is allocated without being freed.</p>
|
||||
<p>To use this kind of checking code, bracket the code you want
|
||||
checked by creating a <code>HeapLeakChecker</code> object at the
|
||||
beginning of the code segment, and call
|
||||
<code>NoLeaks()</code> at the end. These functions, and all others
|
||||
referred to in this file, are declared in
|
||||
<code><gperftools/heap-checker.h></code>.
|
||||
</p>
|
||||
|
||||
<p>Here's an example:</p>
|
||||
<pre>
|
||||
HeapLeakChecker heap_checker("test_foo");
|
||||
{
|
||||
code that exercises some foo functionality;
|
||||
this code should not leak memory;
|
||||
}
|
||||
if (!heap_checker.NoLeaks()) assert(NULL == "heap memory leak");
|
||||
</pre>
|
||||
|
||||
<p>Note that adding in the <code>HeapLeakChecker</code> object merely
|
||||
instruments the code for leak-checking. To actually turn on this
|
||||
leak-checking on a particular run of the executable, you must still
|
||||
run with the heap-checker turned on:</p>
|
||||
<pre>% env HEAPCHECK=local /usr/local/bin/my_binary_compiled_with_tcmalloc</pre>
|
||||
<p>If you want to do whole-program leak checking in addition to this
|
||||
manual leak checking, you can run in <code>normal</code> or some other
|
||||
mode instead: they'll run the "local" checks in addition to the
|
||||
whole-program check.</p>
|
||||
|
||||
|
||||
<h2><a name="disable">Disabling Heap-checking of Known Leaks</a></h2>
|
||||
|
||||
<p>Sometimes your code has leaks that you know about and are willing
|
||||
to accept. You would like the heap checker to ignore them when
|
||||
checking your program. You can do this by bracketing the code in
|
||||
question with an appropriate heap-checking construct:</p>
|
||||
<pre>
|
||||
...
|
||||
{
|
||||
HeapLeakChecker::Disabler disabler;
|
||||
<leaky code>
|
||||
}
|
||||
...
|
||||
</pre>
|
||||
Any objects allocated by <code>leaky code</code> (including inside any
|
||||
routines called by <code>leaky code</code>) and any objects reachable
|
||||
from such objects are not reported as leaks.
|
||||
|
||||
<p>Alternately, you can use <code>IgnoreObject()</code>, which takes a
|
||||
pointer to an object to ignore. That memory, and everything reachable
|
||||
from it (by following pointers), is ignored for the purposes of leak
|
||||
checking. You can call <code>UnIgnoreObject()</code> to undo the
|
||||
effects of <code>IgnoreObject()</code>.</p>
|
||||
|
||||
|
||||
<h2><a name="options">Tuning the Heap Checker</h2>
|
||||
|
||||
<p>The heap leak checker has many options, some that trade off running
|
||||
time and accuracy, and others that increase the sensitivity at the
|
||||
risk of returning false positives. For most uses, the range covered
|
||||
by the <A HREF="#types">heap-check flavors</A> is enough, but in
|
||||
specialized cases more control can be helpful.</p>
|
||||
|
||||
<p>
|
||||
These options are specified via environment varaiables.
|
||||
</p>
|
||||
|
||||
<p>This first set of options controls sensitivity and accuracy. These
|
||||
options are ignored unless you run the heap checker in <A
|
||||
HREF="#types">as-is</A> mode.
|
||||
|
||||
<table frame=box rules=sides cellpadding=5 width=100%>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>HEAP_CHECK_AFTER_DESTRUCTORS</code></td>
|
||||
<td>Default: false</td>
|
||||
<td>
|
||||
When true, do the final leak check after all other global
|
||||
destructors have run. When false, do it after all
|
||||
<code>REGISTER_HEAPCHECK_CLEANUP</code>, typically much earlier in
|
||||
the global-destructor process.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>HEAP_CHECK_IGNORE_THREAD_LIVE</code></td>
|
||||
<td>Default: true</td>
|
||||
<td>
|
||||
If true, ignore objects reachable from thread stacks and registers
|
||||
(that is, do not report them as leaks).
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>HEAP_CHECK_IGNORE_GLOBAL_LIVE</code></td>
|
||||
<td>Default: true</td>
|
||||
<td>
|
||||
If true, ignore objects reachable from global variables and data
|
||||
(that is, do not report them as leaks).
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
</table>
|
||||
|
||||
<p>These options modify the behavior of whole-program leak
|
||||
checking.</p>
|
||||
|
||||
<table frame=box rules=sides cellpadding=5 width=100%>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>HEAP_CHECK_MAX_LEAKS</code></td>
|
||||
<td>Default: 20</td>
|
||||
<td>
|
||||
The maximum number of leaks to be printed to stderr (all leaks are still
|
||||
emitted to file output for pprof to visualize). If negative or zero,
|
||||
print all the leaks found.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
|
||||
</table>
|
||||
|
||||
<p>These options apply to all types of leak checking.</p>
|
||||
|
||||
<table frame=box rules=sides cellpadding=5 width=100%>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>HEAP_CHECK_IDENTIFY_LEAKS</code></td>
|
||||
<td>Default: false</td>
|
||||
<td>
|
||||
If true, generate the addresses of the leaked objects in the
|
||||
generated memory leak profile files.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>HEAP_CHECK_TEST_POINTER_ALIGNMENT</code></td>
|
||||
<td>Default: false</td>
|
||||
<td>
|
||||
If true, check all leaks to see if they might be due to the use
|
||||
of unaligned pointers.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>HEAP_CHECK_POINTER_SOURCE_ALIGNMENT</code></td>
|
||||
<td>Default: sizeof(void*)</td>
|
||||
<td>
|
||||
Alignment at which all pointers in memory are supposed to be located.
|
||||
Use 1 if any alignment is ok.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>PPROF_PATH</code></td>
|
||||
<td>Default: pprof</td>
|
||||
<td>
|
||||
The location of the <code>pprof</code> executable.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>HEAP_CHECK_DUMP_DIRECTORY</code></td>
|
||||
<td>Default: /tmp</td>
|
||||
<td>
|
||||
Where the heap-profile files are kept while the program is running.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
</table>
|
||||
|
||||
|
||||
<h2>Tips for Handling Detected Leaks</h2>
|
||||
|
||||
<p>What do you do when the heap leak checker detects a memory leak?
|
||||
First, you should run the reported <code>pprof</code> command;
|
||||
hopefully, that is enough to track down the location where the leak
|
||||
occurs.</p>
|
||||
|
||||
<p>If the leak is a real leak, you should fix it!</p>
|
||||
|
||||
<p>If you are sure that the reported leaks are not dangerous and there
|
||||
is no good way to fix them, then you can use
|
||||
<code>HeapLeakChecker::Disabler</code> and/or
|
||||
<code>HeapLeakChecker::IgnoreObject()</code> to disable heap-checking
|
||||
for certain parts of the codebase.</p>
|
||||
|
||||
<p>In "strict" or "draconian" mode, leaks may be due to incomplete
|
||||
cleanup in the destructors of global variables. If you don't wish to
|
||||
augment the cleanup routines, but still want to run in "strict" or
|
||||
"draconian" mode, consider using <A
|
||||
HREF="#tweaking"><code>REGISTER_HEAPCHECK_CLEANUP</code></A>.</p>
|
||||
|
||||
<h2>Hints for Debugging Detected Leaks</h2>
|
||||
|
||||
<p>Sometimes it can be useful to not only know the exact code that
|
||||
allocates the leaked objects, but also the addresses of the leaked objects.
|
||||
Combining this e.g. with additional logging in the program
|
||||
one can then track which subset of the allocations
|
||||
made at a certain spot in the code are leaked.
|
||||
<br/>
|
||||
To get the addresses of all leaked objects
|
||||
define the environment variable <code>HEAP_CHECK_IDENTIFY_LEAKS</code>
|
||||
to be <code>1</code>.
|
||||
The object addresses will be reported in the form of addresses
|
||||
of fake immediate callers of the memory allocation routines.
|
||||
Note that the performance of doing leak-checking in this mode
|
||||
can be noticeably worse than the default mode.
|
||||
</p>
|
||||
|
||||
<p>One relatively common class of leaks that don't look real
|
||||
is the case of multiple initialization.
|
||||
In such cases the reported leaks are typically things that are
|
||||
linked from some global objects,
|
||||
which are initialized and say never modified again.
|
||||
The non-obvious cause of the leak is frequently the fact that
|
||||
the initialization code for these objects executes more than once.
|
||||
<br/>
|
||||
E.g. if the code of some <code>.cc</code> file is made to be included twice
|
||||
into the binary, then the constructors for global objects defined in that file
|
||||
will execute twice thus leaking the things allocated on the first run.
|
||||
<br/>
|
||||
Similar problems can occur if object initialization is done more explicitly
|
||||
e.g. on demand by a slightly buggy code
|
||||
that does not always ensure only-once initialization.
|
||||
</p>
|
||||
|
||||
<p>
|
||||
A more rare but even more puzzling problem can be use of not properly
|
||||
aligned pointers (maybe inside of not properly aligned objects).
|
||||
Normally such pointers are not followed by the leak checker,
|
||||
hence the objects reachable only via such pointers are reported as leaks.
|
||||
If you suspect this case
|
||||
define the environment variable <code>HEAP_CHECK_TEST_POINTER_ALIGNMENT</code>
|
||||
to be <code>1</code>
|
||||
and then look closely at the generated leak report messages.
|
||||
</p>
|
||||
|
||||
<h1>How It Works</h1>
|
||||
|
||||
<p>When a <code>HeapLeakChecker</code> object is constructed, it dumps
|
||||
a memory-usage profile named
|
||||
<code><prefix>.<name>-beg.heap</code> to a temporary
|
||||
directory. When <code>NoLeaks()</code>
|
||||
is called (for whole-program checking, this happens automatically at
|
||||
program-exit), it dumps another profile, named
|
||||
<code><prefix>.<name>-end.heap</code>.
|
||||
(<code><prefix></code> is typically determined automatically,
|
||||
and <code><name></code> is typically <code>argv[0]</code>.) It
|
||||
then compares the two profiles. If the second profile shows
|
||||
more memory use than the first, the
|
||||
<code>NoLeaks()</code> function will
|
||||
return false. For "whole program" profiling, this will cause the
|
||||
executable to abort (via <code>exit(1)</code>). In all cases, it will
|
||||
print a message on how to process the dumped profiles to locate
|
||||
leaks.</p>
|
||||
|
||||
<h3><A name=live>Detecting Live Objects</A></h3>
|
||||
|
||||
<p>At any point during a program's execution, all memory that is
|
||||
accessible at that time is considered "live." This includes global
|
||||
variables, and also any memory that is reachable by following pointers
|
||||
from a global variable. It also includes all memory reachable from
|
||||
the current stack frame and from current CPU registers (this captures
|
||||
local variables). Finally, it includes the thread equivalents of
|
||||
these: thread-local storage and thread heaps, memory reachable from
|
||||
thread-local storage and thread heaps, and memory reachable from
|
||||
thread CPU registers.</p>
|
||||
|
||||
<p>In all modes except "draconian," live memory is not
|
||||
considered to be a leak. We detect this by doing a liveness flood,
|
||||
traversing pointers to heap objects starting from some initial memory
|
||||
regions we know to potentially contain live pointer data. Note that
|
||||
this flood might potentially not find some (global) live data region
|
||||
to start the flood from. If you find such, please file a bug.</p>
|
||||
|
||||
<p>The liveness flood attempts to treat any properly aligned byte
|
||||
sequences as pointers to heap objects and thinks that it found a good
|
||||
pointer whenever the current heap memory map contains an object with
|
||||
the address whose byte representation we found. Some pointers into
|
||||
not-at-start of object will also work here.</p>
|
||||
|
||||
<p>As a result of this simple approach, it's possible (though
|
||||
unlikely) for the flood to be inexact and occasionally result in
|
||||
leaked objects being erroneously determined to be live. For instance,
|
||||
random bit patterns can happen to look like pointers to leaked heap
|
||||
objects. More likely, stale pointer data not corresponding to any
|
||||
live program variables can be still present in memory regions,
|
||||
especially in thread stacks. For instance, depending on how the local
|
||||
<code>malloc</code> is implemented, it may reuse a heap object
|
||||
address:</p>
|
||||
<pre>
|
||||
char* p = new char[1]; // new might return 0x80000000, say.
|
||||
delete p;
|
||||
new char[1]; // new might return 0x80000000 again
|
||||
// This last new is a leak, but doesn't seem it: p looks like it points to it
|
||||
</pre>
|
||||
|
||||
<p>In other words, imprecisions in the liveness flood mean that for
|
||||
any heap leak check we might miss some memory leaks. This means that
|
||||
for local leak checks, we might report a memory leak in the local
|
||||
area, even though the leak actually happened before the
|
||||
<code>HeapLeakChecker</code> object was constructed. Note that for
|
||||
whole-program checks, a leak report <i>does</i> always correspond to a
|
||||
real leak (since there's no "before" to have created a false-live
|
||||
object).</p>
|
||||
|
||||
<p>While this liveness flood approach is not very portable and not
|
||||
100% accurate, it works in most cases and saves us from writing a lot
|
||||
of explicit clean up code and other hassles when dealing with thread
|
||||
data.</p>
|
||||
|
||||
|
||||
<h3>Visualizing Leak with <code>pprof</code></h3>
|
||||
|
||||
<p>
|
||||
The heap checker automatically prints basic leak info with stack traces of
|
||||
leaked objects' allocation sites, as well as a pprof command line that can be
|
||||
used to visualize the call-graph involved in these allocations.
|
||||
The latter can be much more useful for a human
|
||||
to see where/why the leaks happened, especially if the leaks are numerous.
|
||||
</p>
|
||||
|
||||
<h3>Leak-checking and Threads</h3>
|
||||
|
||||
<p>At the time of HeapLeakChecker's construction and during
|
||||
<code>NoLeaks()</code> calls, we grab a lock
|
||||
and then pause all other threads so other threads do not interfere
|
||||
with recording or analyzing the state of the heap.</p>
|
||||
|
||||
<p>In general, leak checking works correctly in the presence of
|
||||
threads. However, thread stack data liveness determination (via
|
||||
<code>base/thread_lister.h</code>) does not work when the program is
|
||||
running under GDB, because the ptrace functionality needed for finding
|
||||
threads is already hooked to by GDB. Conversely, leak checker's
|
||||
ptrace attempts might also interfere with GDB. As a result, GDB can
|
||||
result in potentially false leak reports. For this reason, the
|
||||
heap-checker turns itself off when running under GDB.</p>
|
||||
|
||||
<p>Also, <code>thread_lister</code> only works for Linux pthreads;
|
||||
leak checking is unlikely to handle other thread implementations
|
||||
correctly.</p>
|
||||
|
||||
<p>As mentioned in the discussion of liveness flooding, thread-stack
|
||||
liveness determination might mis-classify as reachable objects that
|
||||
very recently became unreachable (leaked). This can happen when the
|
||||
pointers to now-logically-unreachable objects are present in the
|
||||
active thread stack frame. In other words, trivial code like the
|
||||
following might not produce the expected leak checking outcome
|
||||
depending on how the compiled code works with the stack:</p>
|
||||
<pre>
|
||||
int* foo = new int [20];
|
||||
HeapLeakChecker check("a_check");
|
||||
foo = NULL;
|
||||
// May fail to trigger.
|
||||
if (!heap_checker.NoLeaks()) assert(NULL == "heap memory leak");
|
||||
</pre>
|
||||
|
||||
|
||||
<hr>
|
||||
<address>Maxim Lifantsev<br>
|
||||
<!-- Created: Tue Dec 19 10:43:14 PST 2000 -->
|
||||
<!-- hhmts start -->
|
||||
Last modified: Fri Jul 13 13:14:33 PDT 2007
|
||||
<!-- hhmts end -->
|
||||
</address>
|
||||
</body>
|
||||
</html>
|
391
trunk/3rdparty/gperftools-2-fit/docs/heapprofile.html
vendored
Normal file
|
@ -0,0 +1,391 @@
|
|||
<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML//EN">
|
||||
<HTML>
|
||||
|
||||
<HEAD>
|
||||
<link rel="stylesheet" href="designstyle.css">
|
||||
<title>Gperftools Heap Profiler</title>
|
||||
</HEAD>
|
||||
|
||||
<BODY>
|
||||
|
||||
<p align=right>
|
||||
<i>Last modified
|
||||
<script type=text/javascript>
|
||||
var lm = new Date(document.lastModified);
|
||||
document.write(lm.toDateString());
|
||||
</script></i>
|
||||
</p>
|
||||
|
||||
<p>This is the heap profiler we use at Google, to explore how C++
|
||||
programs manage memory. This facility can be useful for</p>
|
||||
<ul>
|
||||
<li> Figuring out what is in the program heap at any given time
|
||||
<li> Locating memory leaks
|
||||
<li> Finding places that do a lot of allocation
|
||||
</ul>
|
||||
|
||||
<p>The profiling system instruments all allocations and frees. It
|
||||
keeps track of various pieces of information per allocation site. An
|
||||
allocation site is defined as the active stack trace at the call to
|
||||
<code>malloc</code>, <code>calloc</code>, <code>realloc</code>, or,
|
||||
<code>new</code>.</p>
|
||||
|
||||
<p>There are three parts to using it: linking the library into an
|
||||
application, running the code, and analyzing the output.</p>
|
||||
|
||||
|
||||
<h1>Linking in the Library</h1>
|
||||
|
||||
<p>To install the heap profiler into your executable, add
|
||||
<code>-ltcmalloc</code> to the link-time step for your executable.
|
||||
Also, while we don't necessarily recommend this form of usage, it's
|
||||
possible to add in the profiler at run-time using
|
||||
<code>LD_PRELOAD</code>:
|
||||
<pre>% env LD_PRELOAD="/usr/lib/libtcmalloc.so" <binary></pre>
|
||||
|
||||
<p>This does <i>not</i> turn on heap profiling; it just inserts the
|
||||
code. For that reason, it's practical to just always link
|
||||
<code>-ltcmalloc</code> into a binary while developing; that's what we
|
||||
do at Google. (However, since any user can turn on the profiler by
|
||||
setting an environment variable, it's not necessarily recommended to
|
||||
install profiler-linked binaries into a production, running
|
||||
system.) Note that if you wish to use the heap profiler, you must
|
||||
also use the tcmalloc memory-allocation library. There is no way
|
||||
currently to use the heap profiler separate from tcmalloc.</p>
|
||||
|
||||
|
||||
<h1>Running the Code</h1>
|
||||
|
||||
<p>There are several alternatives to actually turn on heap profiling
|
||||
for a given run of an executable:</p>
|
||||
|
||||
<ol>
|
||||
<li> <p>Define the environment variable HEAPPROFILE to the filename
|
||||
to dump the profile to. For instance, to profile
|
||||
<code>/usr/local/bin/my_binary_compiled_with_tcmalloc</code>:</p>
|
||||
<pre>% env HEAPPROFILE=/tmp/mybin.hprof /usr/local/bin/my_binary_compiled_with_tcmalloc</pre>
|
||||
<li> <p>In your code, bracket the code you want profiled in calls to
|
||||
<code>HeapProfilerStart()</code> and <code>HeapProfilerStop()</code>.
|
||||
(These functions are declared in <code><gperftools/heap-profiler.h></code>.)
|
||||
<code>HeapProfilerStart()</code> will take the
|
||||
profile-filename-prefix as an argument. Then, as often as
|
||||
you'd like before calling <code>HeapProfilerStop()</code>, you
|
||||
can use <code>HeapProfilerDump()</code> or
|
||||
<code>GetHeapProfile()</code> to examine the profile. In case
|
||||
it's useful, <code>IsHeapProfilerRunning()</code> will tell you
|
||||
whether you've already called HeapProfilerStart() or not.</p>
|
||||
</ol>
|
||||
|
||||
|
||||
<p>For security reasons, heap profiling will not write to a file --
|
||||
and is thus not usable -- for setuid programs.</p>
|
||||
|
||||
<H2>Modifying Runtime Behavior</H2>
|
||||
|
||||
<p>You can more finely control the behavior of the heap profiler via
|
||||
environment variables.</p>
|
||||
|
||||
<table frame=box rules=sides cellpadding=5 width=100%>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>HEAP_PROFILE_ALLOCATION_INTERVAL</code></td>
|
||||
<td>default: 1073741824 (1 Gb)</td>
|
||||
<td>
|
||||
Dump heap profiling information each time the specified number of
|
||||
bytes has been allocated by the program.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>HEAP_PROFILE_INUSE_INTERVAL</code></td>
|
||||
<td>default: 104857600 (100 Mb)</td>
|
||||
<td>
|
||||
Dump heap profiling information whenever the high-water memory
|
||||
usage mark increases by the specified number of bytes.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>HEAP_PROFILE_TIME_INTERVAL</code></td>
|
||||
<td>default: 0</td>
|
||||
<td>
|
||||
Dump heap profiling information each time the specified
|
||||
number of seconds has elapsed.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>HEAPPROFILESIGNAL</code></td>
|
||||
<td>default: disabled</td>
|
||||
<td>
|
||||
Dump heap profiling information whenever the specified signal is sent to the
|
||||
process.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>HEAP_PROFILE_MMAP</code></td>
|
||||
<td>default: false</td>
|
||||
<td>
|
||||
Profile <code>mmap</code>, <code>mremap</code> and <code>sbrk</code>
|
||||
calls in addition
|
||||
to <code>malloc</code>, <code>calloc</code>, <code>realloc</code>,
|
||||
and <code>new</code>. <b>NOTE:</b> this causes the profiler to
|
||||
profile calls internal to tcmalloc, since tcmalloc and friends use
|
||||
mmap and sbrk internally for allocations. One partial solution is
|
||||
to filter these allocations out when running <code>pprof</code>,
|
||||
with something like
|
||||
<code>pprof --ignore='DoAllocWithArena|SbrkSysAllocator::Alloc|MmapSysAllocator::Alloc</code>.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>HEAP_PROFILE_ONLY_MMAP</code></td>
|
||||
<td>default: false</td>
|
||||
<td>
|
||||
Only profile <code>mmap</code>, <code>mremap</code>, and <code>sbrk</code>
|
||||
calls; do not profile
|
||||
<code>malloc</code>, <code>calloc</code>, <code>realloc</code>,
|
||||
or <code>new</code>.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>HEAP_PROFILE_MMAP_LOG</code></td>
|
||||
<td>default: false</td>
|
||||
<td>
|
||||
Log <code>mmap</code>/<code>munmap</code> calls.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
</table>
|
||||
|
||||
<H2>Checking for Leaks</H2>
|
||||
|
||||
<p>You can use the heap profiler to manually check for leaks, for
|
||||
instance by reading the profiler output and looking for large
|
||||
allocations. However, for that task, it's easier to use the <A
|
||||
HREF="heap_checker.html">automatic heap-checking facility</A> built
|
||||
into tcmalloc.</p>
|
||||
|
||||
|
||||
<h1><a name="pprof">Analyzing the Output</a></h1>
|
||||
|
||||
<p>If heap-profiling is turned on in a program, the program will
|
||||
periodically write profiles to the filesystem. The sequence of
|
||||
profiles will be named:</p>
|
||||
<pre>
|
||||
<prefix>.0000.heap
|
||||
<prefix>.0001.heap
|
||||
<prefix>.0002.heap
|
||||
...
|
||||
</pre>
|
||||
<p>where <code><prefix></code> is the filename-prefix supplied
|
||||
when running the code (e.g. via the <code>HEAPPROFILE</code>
|
||||
environment variable). Note that if the supplied prefix
|
||||
does not start with a <code>/</code>, the profile files will be
|
||||
written to the program's working directory.</p>
|
||||
|
||||
<p>The profile output can be viewed by passing it to the
|
||||
<code>pprof</code> tool -- the same tool that's used to analyze <A
|
||||
HREF="cpuprofile.html">CPU profiles</A>.
|
||||
|
||||
<p>Here are some examples. These examples assume the binary is named
|
||||
<code>gfs_master</code>, and a sequence of heap profile files can be
|
||||
found in files named:</p>
|
||||
<pre>
|
||||
/tmp/profile.0001.heap
|
||||
/tmp/profile.0002.heap
|
||||
...
|
||||
/tmp/profile.0100.heap
|
||||
</pre>
|
||||
|
||||
<h3>Why is a process so big</h3>
|
||||
|
||||
<pre>
|
||||
% pprof --gv gfs_master /tmp/profile.0100.heap
|
||||
</pre>
|
||||
|
||||
<p>This command will pop-up a <code>gv</code> window that displays
|
||||
the profile information as a directed graph. Here is a portion
|
||||
of the resulting output:</p>
|
||||
|
||||
<p><center>
|
||||
<img src="heap-example1.png">
|
||||
</center></p>
|
||||
|
||||
A few explanations:
|
||||
<ul>
|
||||
<li> <code>GFS_MasterChunk::AddServer</code> accounts for 255.6 MB
|
||||
of the live memory, which is 25% of the total live memory.
|
||||
<li> <code>GFS_MasterChunkTable::UpdateState</code> is directly
|
||||
accountable for 176.2 MB of the live memory (i.e., it directly
|
||||
allocated 176.2 MB that has not been freed yet). Furthermore,
|
||||
it and its callees are responsible for 729.9 MB. The
|
||||
labels on the outgoing edges give a good indication of the
|
||||
amount allocated by each callee.
|
||||
</ul>
|
||||
|
||||
<h3>Comparing Profiles</h3>
|
||||
|
||||
<p>You often want to skip allocations during the initialization phase
|
||||
of a program so you can find gradual memory leaks. One simple way to
|
||||
do this is to compare two profiles -- both collected after the program
|
||||
has been running for a while. Specify the name of the first profile
|
||||
using the <code>--base</code> option. For example:</p>
|
||||
<pre>
|
||||
% pprof --base=/tmp/profile.0004.heap gfs_master /tmp/profile.0100.heap
|
||||
</pre>
|
||||
|
||||
<p>The memory-usage in <code>/tmp/profile.0004.heap</code> will be
|
||||
subtracted from the memory-usage in
|
||||
<code>/tmp/profile.0100.heap</code> and the result will be
|
||||
displayed.</p>
|
||||
|
||||
<h3>Text display</h3>
|
||||
|
||||
<pre>
|
||||
% pprof --text gfs_master /tmp/profile.0100.heap
|
||||
255.6 24.7% 24.7% 255.6 24.7% GFS_MasterChunk::AddServer
|
||||
184.6 17.8% 42.5% 298.8 28.8% GFS_MasterChunkTable::Create
|
||||
176.2 17.0% 59.5% 729.9 70.5% GFS_MasterChunkTable::UpdateState
|
||||
169.8 16.4% 75.9% 169.8 16.4% PendingClone::PendingClone
|
||||
76.3 7.4% 83.3% 76.3 7.4% __default_alloc_template::_S_chunk_alloc
|
||||
49.5 4.8% 88.0% 49.5 4.8% hashtable::resize
|
||||
...
|
||||
</pre>
|
||||
|
||||
<p>
|
||||
<ul>
|
||||
<li> The first column contains the direct memory use in MB.
|
||||
<li> The fourth column contains memory use by the procedure
|
||||
and all of its callees.
|
||||
<li> The second and fifth columns are just percentage
|
||||
representations of the numbers in the first and fourth columns.
|
||||
<li> The third column is a cumulative sum of the second column
|
||||
(i.e., the <code>k</code>th entry in the third column is the
|
||||
sum of the first <code>k</code> entries in the second column.)
|
||||
</ul>
|
||||
|
||||
<h3>Ignoring or focusing on specific regions</h3>
|
||||
|
||||
<p>The following command will give a graphical display of a subset of
|
||||
the call-graph. Only paths in the call-graph that match the regular
|
||||
expression <code>DataBuffer</code> are included:</p>
|
||||
<pre>
|
||||
% pprof --gv --focus=DataBuffer gfs_master /tmp/profile.0100.heap
|
||||
</pre>
|
||||
|
||||
<p>Similarly, the following command will omit all paths subset of the
|
||||
call-graph. All paths in the call-graph that match the regular
|
||||
expression <code>DataBuffer</code> are discarded:</p>
|
||||
<pre>
|
||||
% pprof --gv --ignore=DataBuffer gfs_master /tmp/profile.0100.heap
|
||||
</pre>
|
||||
|
||||
<h3>Total allocations + object-level information</h3>
|
||||
|
||||
<p>All of the previous examples have displayed the amount of in-use
|
||||
space. I.e., the number of bytes that have been allocated but not
|
||||
freed. You can also get other types of information by supplying a
|
||||
flag to <code>pprof</code>:</p>
|
||||
|
||||
<center>
|
||||
<table frame=box rules=sides cellpadding=5 width=100%>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>--inuse_space</code></td>
|
||||
<td>
|
||||
Display the number of in-use megabytes (i.e. space that has
|
||||
been allocated but not freed). This is the default.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>--inuse_objects</code></td>
|
||||
<td>
|
||||
Display the number of in-use objects (i.e. number of
|
||||
objects that have been allocated but not freed).
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>--alloc_space</code></td>
|
||||
<td>
|
||||
Display the number of allocated megabytes. This includes
|
||||
the space that has since been de-allocated. Use this
|
||||
if you want to find the main allocation sites in the
|
||||
program.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>--alloc_objects</code></td>
|
||||
<td>
|
||||
Display the number of allocated objects. This includes
|
||||
the objects that have since been de-allocated. Use this
|
||||
if you want to find the main allocation sites in the
|
||||
program.
|
||||
</td>
|
||||
|
||||
</table>
|
||||
</center>
|
||||
|
||||
|
||||
<h3>Interactive mode</a></h3>
|
||||
|
||||
<p>By default -- if you don't specify any flags to the contrary --
|
||||
pprof runs in interactive mode. At the <code>(pprof)</code> prompt,
|
||||
you can run many of the commands described above. You can type
|
||||
<code>help</code> for a list of what commands are available in
|
||||
interactive mode.</p>
|
||||
|
||||
|
||||
<h1>Caveats</h1>
|
||||
|
||||
<ul>
|
||||
<li> Heap profiling requires the use of libtcmalloc. This
|
||||
requirement may be removed in a future version of the heap
|
||||
profiler, and the heap profiler separated out into its own
|
||||
library.
|
||||
|
||||
<li> If the program linked in a library that was not compiled
|
||||
with enough symbolic information, all samples associated
|
||||
with the library may be charged to the last symbol found
|
||||
in the program before the library. This will artificially
|
||||
inflate the count for that symbol.
|
||||
|
||||
<li> If you run the program on one machine, and profile it on
|
||||
another, and the shared libraries are different on the two
|
||||
machines, the profiling output may be confusing: samples that
|
||||
fall within the shared libaries may be assigned to arbitrary
|
||||
procedures.
|
||||
|
||||
<li> Several libraries, such as some STL implementations, do their
|
||||
own memory management. This may cause strange profiling
|
||||
results. We have code in libtcmalloc to cause STL to use
|
||||
tcmalloc for memory management (which in our tests is better
|
||||
than STL's internal management), though it only works for some
|
||||
STL implementations.
|
||||
|
||||
<li> If your program forks, the children will also be profiled
|
||||
(since they inherit the same HEAPPROFILE setting). Each
|
||||
process is profiled separately; to distinguish the child
|
||||
profiles from the parent profile and from each other, all
|
||||
children will have their process-id attached to the HEAPPROFILE
|
||||
name.
|
||||
|
||||
<li> Due to a hack we make to work around a possible gcc bug, your
|
||||
profiles may end up named strangely if the first character of
|
||||
your HEAPPROFILE variable has ascii value greater than 127.
|
||||
This should be exceedingly rare, but if you need to use such a
|
||||
name, just set prepend <code>./</code> to your filename:
|
||||
<code>HEAPPROFILE=./Ägypten</code>.
|
||||
</ul>
|
||||
|
||||
<hr>
|
||||
<address>Sanjay Ghemawat
|
||||
<!-- Created: Tue Dec 19 10:43:14 PST 2000 -->
|
||||
</address>
|
||||
</body>
|
||||
</html>
|
20
trunk/3rdparty/gperftools-2-fit/docs/index.html
vendored
Normal file
|
@ -0,0 +1,20 @@
|
|||
<HTML>
|
||||
|
||||
<HEAD>
|
||||
<title>Gperftools</title>
|
||||
</HEAD>
|
||||
|
||||
<BODY>
|
||||
<ul>
|
||||
<li> <A HREF="tcmalloc.html">thread-caching malloc</A>
|
||||
<li> <A HREF="heap_checker.html">heap-checking using tcmalloc</A>
|
||||
<li> <A HREF="heapprofile.html">heap-profiling using tcmalloc</A>
|
||||
<li> <A HREF="cpuprofile.html">CPU profiler</A>
|
||||
</ul>
|
||||
|
||||
<hr>
|
||||
Last modified: Thu Feb 2 14:40:47 PST 2012
|
||||
|
||||
</BODY>
|
||||
|
||||
</HTML>
|
15
trunk/3rdparty/gperftools-2-fit/docs/overview.dot
vendored
Normal file
|
@ -0,0 +1,15 @@
|
|||
digraph Overview {
|
||||
node [shape = box]
|
||||
|
||||
{rank=same
|
||||
T1 [label="Thread Cache"]
|
||||
Tsep [label="...", shape=plaintext]
|
||||
Tn [label="Thread Cache"]
|
||||
T1 -> Tsep -> Tn [style=invis]
|
||||
}
|
||||
|
||||
C [label="Central\nHeap"]
|
||||
T1 -> C [dir=both]
|
||||
Tn -> C [dir=both]
|
||||
|
||||
}
|
BIN
trunk/3rdparty/gperftools-2-fit/docs/overview.gif
vendored
Normal file
After Width: | Height: | Size: 6.3 KiB |
25
trunk/3rdparty/gperftools-2-fit/docs/pageheap.dot
vendored
Normal file
|
@ -0,0 +1,25 @@
|
|||
digraph PageHeap {
|
||||
rankdir=LR
|
||||
node [shape=box, width=0.3, height=0.3]
|
||||
nodesep=.05
|
||||
|
||||
heap [shape=record, height=3, label="<f0>1 page|<f1>2 pages|<f2>3 pages|...|<f128>128 pages"]
|
||||
O0 [shape=record, label=""]
|
||||
O1 [shape=record, label=""]
|
||||
O2 [shape=record, label="{|}"]
|
||||
O3 [shape=record, label="{|}"]
|
||||
O4 [shape=record, label="{||}"]
|
||||
O5 [shape=record, label="{||}"]
|
||||
O6 [shape=record, label="{|...|}"]
|
||||
O7 [shape=record, label="{|...|}"]
|
||||
sep1 [shape=plaintext, label="..."]
|
||||
sep2 [shape=plaintext, label="..."]
|
||||
sep3 [shape=plaintext, label="..."]
|
||||
sep4 [shape=plaintext, label="..."]
|
||||
|
||||
heap:f0 -> O0 -> O1 -> sep1
|
||||
heap:f1 -> O2 -> O3 -> sep2
|
||||
heap:f2 -> O4 -> O5 -> sep3
|
||||
heap:f128 -> O6 -> O7 -> sep4
|
||||
|
||||
}
|
BIN
trunk/3rdparty/gperftools-2-fit/docs/pageheap.gif
vendored
Normal file
After Width: | Height: | Size: 5.8 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/pprof-test-big.gif
vendored
Normal file
After Width: | Height: | Size: 109 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/pprof-test.gif
vendored
Normal file
After Width: | Height: | Size: 56 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/pprof-vsnprintf-big.gif
vendored
Normal file
After Width: | Height: | Size: 98 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/pprof-vsnprintf.gif
vendored
Normal file
After Width: | Height: | Size: 30 KiB |
131
trunk/3rdparty/gperftools-2-fit/docs/pprof.1
vendored
Normal file
|
@ -0,0 +1,131 @@
|
|||
.\" DO NOT MODIFY THIS FILE! It was generated by help2man 1.23.
|
||||
.TH PPROF "1" "February 2005" "pprof (part of gperftools)" Google
|
||||
.SH NAME
|
||||
pprof \- manual page for pprof (part of gperftools)
|
||||
.SH SYNOPSIS
|
||||
.B pprof
|
||||
[\fIoptions\fR] \fI<program> <profile>\fR
|
||||
.SH DESCRIPTION
|
||||
.IP
|
||||
Prints specified cpu- or heap-profile
|
||||
.SH OPTIONS
|
||||
.TP
|
||||
\fB\-\-cum\fR
|
||||
Sort by cumulative data
|
||||
.TP
|
||||
\fB\-\-base=\fR<base>
|
||||
Subtract <base> from <profile> before display
|
||||
.SS "Reporting Granularity:"
|
||||
.TP
|
||||
\fB\-\-addresses\fR
|
||||
Report at address level
|
||||
.TP
|
||||
\fB\-\-lines\fR
|
||||
Report at source line level
|
||||
.TP
|
||||
\fB\-\-functions\fR
|
||||
Report at function level [default]
|
||||
.TP
|
||||
\fB\-\-files\fR
|
||||
Report at source file level
|
||||
.SS "Output type:"
|
||||
.TP
|
||||
\fB\-\-text\fR
|
||||
Generate text report [default]
|
||||
.TP
|
||||
\fB\-\-gv\fR
|
||||
Generate Postscript and display
|
||||
.TP
|
||||
\fB\-\-list=\fR<regexp>
|
||||
Generate source listing of matching routines
|
||||
.TP
|
||||
\fB\-\-disasm=\fR<regexp>
|
||||
Generate disassembly of matching routines
|
||||
.TP
|
||||
\fB\-\-dot\fR
|
||||
Generate DOT file to stdout
|
||||
.TP
|
||||
\fB\-\-ps\fR
|
||||
Generate Postscript to stdout
|
||||
.TP
|
||||
\fB\-\-pdf\fR
|
||||
Generate PDF to stdout
|
||||
.TP
|
||||
\fB\-\-gif\fR
|
||||
Generate GIF to stdout
|
||||
.SS "Heap-Profile Options:"
|
||||
.TP
|
||||
\fB\-\-inuse_space\fR
|
||||
Display in-use (mega)bytes [default]
|
||||
.TP
|
||||
\fB\-\-inuse_objects\fR
|
||||
Display in-use objects
|
||||
.TP
|
||||
\fB\-\-alloc_space\fR
|
||||
Display allocated (mega)bytes
|
||||
.TP
|
||||
\fB\-\-alloc_objects\fR
|
||||
Display allocated objects
|
||||
.TP
|
||||
\fB\-\-show_bytes\fR
|
||||
Display space in bytes
|
||||
.TP
|
||||
\fB\-\-drop_negative\fR
|
||||
Ignore negaive differences
|
||||
.SS "Call-graph Options:"
|
||||
.TP
|
||||
\fB\-\-nodecount=\fR<n>
|
||||
Show at most so many nodes [default=80]
|
||||
.TP
|
||||
\fB\-\-nodefraction=\fR<f>
|
||||
Hide nodes below <f>*total [default=.005]
|
||||
.TP
|
||||
\fB\-\-edgefraction=\fR<f>
|
||||
Hide edges below <f>*total [default=.001]
|
||||
.TP
|
||||
\fB\-\-focus=\fR<regexp>
|
||||
Focus on nodes matching <regexp>
|
||||
.TP
|
||||
\fB\-\-ignore=\fR<regexp>
|
||||
Ignore nodes matching <regexp>
|
||||
.TP
|
||||
\fB\-\-scale=\fR<n>
|
||||
Set GV scaling [default=0]
|
||||
.SH EXAMPLES
|
||||
|
||||
pprof /bin/ls ls.prof
|
||||
.IP
|
||||
Outputs one line per procedure
|
||||
.PP
|
||||
pprof \fB\-\-gv\fR /bin/ls ls.prof
|
||||
.IP
|
||||
Displays annotated call-graph via 'gv'
|
||||
.PP
|
||||
pprof \fB\-\-gv\fR \fB\-\-focus\fR=\fIMutex\fR /bin/ls ls.prof
|
||||
.IP
|
||||
Restricts to code paths including a .*Mutex.* entry
|
||||
.PP
|
||||
pprof \fB\-\-gv\fR \fB\-\-focus\fR=\fIMutex\fR \fB\-\-ignore\fR=\fIstring\fR /bin/ls ls.prof
|
||||
.IP
|
||||
Code paths including Mutex but not string
|
||||
.PP
|
||||
pprof \fB\-\-list\fR=\fIgetdir\fR /bin/ls ls.prof
|
||||
.IP
|
||||
Dissassembly (with per-line annotations) for getdir()
|
||||
.PP
|
||||
pprof \fB\-\-disasm\fR=\fIgetdir\fR /bin/ls ls.prof
|
||||
.IP
|
||||
Dissassembly (with per-PC annotations) for getdir()
|
||||
.SH COPYRIGHT
|
||||
Copyright \(co 2005 Google Inc.
|
||||
.SH "SEE ALSO"
|
||||
Further documentation for
|
||||
.B pprof
|
||||
is maintained as a web page called
|
||||
.B cpu_profiler.html
|
||||
and is likely installed at one of the following locations:
|
||||
.IP
|
||||
.B /usr/share/gperftools/cpu_profiler.html
|
||||
.br
|
||||
.B /usr/local/share/gperftools/cpu_profiler.html
|
||||
.PP
|
11
trunk/3rdparty/gperftools-2-fit/docs/pprof.see_also
vendored
Normal file
|
@ -0,0 +1,11 @@
|
|||
[see also]
|
||||
Further documentation for
|
||||
.B pprof
|
||||
is maintained as a web page called
|
||||
.B cpu_profiler.html
|
||||
and is likely installed at one of the following locations:
|
||||
.IP
|
||||
.B /usr/share/gperftools/cpu_profiler.html
|
||||
.br
|
||||
.B /usr/local/share/gperftools/cpu_profiler.html
|
||||
.PP
|
260
trunk/3rdparty/gperftools-2-fit/docs/pprof_remote_servers.html
vendored
Normal file
|
@ -0,0 +1,260 @@
|
|||
<HTML>
|
||||
|
||||
<HEAD>
|
||||
<title>pprof and Remote Servers</title>
|
||||
</HEAD>
|
||||
|
||||
<BODY>
|
||||
|
||||
<h1><code>pprof</code> and Remote Servers</h1>
|
||||
|
||||
<p>In mid-2006, we added an experimental facility to <A
|
||||
HREF="cpu_profiler.html">pprof</A>, the tool that analyzes CPU and
|
||||
heap profiles. This facility allows you to collect profile
|
||||
information from running applications. It makes it easy to collect
|
||||
profile information without having to stop the program first, and
|
||||
without having to log into the machine where the application is
|
||||
running. This is meant to be used on webservers, but will work on any
|
||||
application that can be modified to accept TCP connections on a port
|
||||
of its choosing, and to respond to HTTP requests on that port.</p>
|
||||
|
||||
<p>We do not currently have infrastructure, such as apache modules,
|
||||
that you can pop into a webserver or other application to get the
|
||||
necessary functionality "for free." However, it's easy to generate
|
||||
the necessary data, which should allow the interested developer to add
|
||||
the necessary support into his or her applications.</p>
|
||||
|
||||
<p>To use <code>pprof</code> in this experimental "server" mode, you
|
||||
give the script a host and port it should query, replacing the normal
|
||||
commandline arguments of application + profile file:</p>
|
||||
<pre>
|
||||
% pprof internalweb.mycompany.com:80
|
||||
</pre>
|
||||
|
||||
<p>The host must be listening on that port, and be able to accept HTTP/1.0
|
||||
requests -- sent via <code>wget</code> and <code>curl</code> -- for
|
||||
several urls. The following sections list the urls that
|
||||
<code>pprof</code> can send, and the responses it expects in
|
||||
return.</p>
|
||||
|
||||
<p>Here are examples that pprof will recognize, when you give them
|
||||
on the commandline, are urls. In general, you
|
||||
specify the host and a port (the port-number is required), and put
|
||||
the service-name at the end of the url.:</p>
|
||||
<blockquote><pre>
|
||||
http://myhost:80/pprof/heap # retrieves a heap profile
|
||||
http://myhost:8008/pprof/profile # retrieves a CPU profile
|
||||
http://myhost:80 # retrieves a CPU profile (the default)
|
||||
http://myhost:8080/ # retrieves a CPU profile (the default)
|
||||
myhost:8088/pprof/growth # "http://" is optional, but port is not
|
||||
http://myhost:80/myservice/pprof/heap # /pprof/heap just has to come at the end
|
||||
http://myhost:80/pprof/pmuprofile # CPU profile using performance counters
|
||||
</pre></blockquote>
|
||||
|
||||
<h2> <code><b>/pprof/heap</b></code> </h2>
|
||||
|
||||
<p><code>pprof</code> asks for the url <code>/pprof/heap</code> to
|
||||
get heap information. The actual url is controlled via the variable
|
||||
<code>HEAP_PAGE</code> in the <code>pprof</code> script, so you
|
||||
can change it if you'd like.</p>
|
||||
|
||||
<p>There are two ways to get this data. The first is to call</p>
|
||||
<pre>
|
||||
MallocExtension::instance()->GetHeapSample(&output);
|
||||
</pre>
|
||||
<p>and have the server send <code>output</code> back as an HTTP
|
||||
response to <code>pprof</code>. <code>MallocExtension</code> is
|
||||
defined in the header file <code>gperftools/malloc_extension.h</code>.</p>
|
||||
|
||||
<p>Note this will only only work if the binary is being run with
|
||||
sampling turned on (which is not the default). To do this, set the
|
||||
environment variable <code>TCMALLOC_SAMPLE_PARAMETER</code> to a
|
||||
positive value, such as 524288, before running.</p>
|
||||
|
||||
<p>The other way is to call <code>HeapProfileStart(filename)</code>
|
||||
(from <code>heap-profiler.h</code>), continue to do work, and then,
|
||||
some number of seconds later, call <code>GetHeapProfile()</code>
|
||||
(followed by <code>HeapProfilerStop()</code>). The server can send
|
||||
the output of <code>GetHeapProfile</code> back as the HTTP response to
|
||||
pprof. (Note you must <code>free()</code> this data after using it.)
|
||||
This is similar to how <A HREF="#profile">profile requests</A> are
|
||||
handled, below. This technique does not require the application to
|
||||
run with sampling turned on.</p>
|
||||
|
||||
<p>Here's an example of what the output should look like:</p>
|
||||
<pre>
|
||||
heap profile: 1923: 127923432 [ 1923: 127923432] @ heap_v2/524288
|
||||
1: 312 [ 1: 312] @ 0x2aaaabaf5ccc 0x2aaaaba4cd2c 0x2aaaac08c09a
|
||||
928: 122586016 [ 928: 122586016] @ 0x2aaaabaf682c 0x400680 0x400bdd 0x2aaaab1c368a 0x2aaaab1c8f77 0x2aaaab1c0396 0x2aaaab1c86ed 0x4007ff 0x2aaaaca62afa
|
||||
1: 16 [ 1: 16] @ 0x2aaaabaf5ccc 0x2aaaabb04bac 0x2aaaabc1b262 0x2aaaabc21496 0x2aaaabc214bb
|
||||
[...]
|
||||
</pre>
|
||||
|
||||
|
||||
<p> Older code may produce "version 1" heap profiles which look like this:<p/>
|
||||
<pre>
|
||||
heap profile: 14933: 791700132 [ 14933: 791700132] @ heap
|
||||
1: 848688 [ 1: 848688] @ 0xa4b142 0x7f5bfc 0x87065e 0x4056e9 0x4125f8 0x42b4f1 0x45b1ba 0x463248 0x460871 0x45cb7c 0x5f1744 0x607cee 0x5f4a5e 0x40080f 0x2aaaabad7afa
|
||||
1: 1048576 [ 1: 1048576] @ 0xa4a9b2 0x7fd025 0x4ca6d8 0x4ca814 0x4caa88 0x2aaaab104cf0 0x404e20 0x4125f8 0x42b4f1 0x45b1ba 0x463248 0x460871 0x45cb7c 0x5f1744 0x607cee 0x5f4a5e 0x40080f 0x2aaaabad7afa
|
||||
2942: 388629374 [ 2942: 388629374] @ 0xa4b142 0x4006a0 0x400bed 0x5f0cfa 0x5f1744 0x607cee 0x5f4a5e 0x40080f 0x2aaaabad7afa
|
||||
[...]
|
||||
</pre>
|
||||
<p>pprof accepts both old and new heap profiles and automatically
|
||||
detects which one you are using.</p>
|
||||
|
||||
<h2> <code><b>/pprof/growth</b></code> </h2>
|
||||
|
||||
<p><code>pprof</code> asks for the url <code>/pprof/growth</code> to
|
||||
get heap-profiling delta (growth) information. The actual url is
|
||||
controlled via the variable <code>GROWTH_PAGE</code> in the
|
||||
<code>pprof</code> script, so you can change it if you'd like.</p>
|
||||
|
||||
<p>The server should respond by calling</p>
|
||||
<pre>
|
||||
MallocExtension::instance()->GetHeapGrowthStacks(&output);
|
||||
</pre>
|
||||
<p>and sending <code>output</code> back as an HTTP response to
|
||||
<code>pprof</code>. <code>MallocExtension</code> is defined in the
|
||||
header file <code>gperftools/malloc_extension.h</code>.</p>
|
||||
|
||||
<p>Here's an example, from an actual Google webserver, of what the
|
||||
output should look like:</p>
|
||||
<pre>
|
||||
heap profile: 741: 812122112 [ 741: 812122112] @ growth
|
||||
1: 1572864 [ 1: 1572864] @ 0x87da564 0x87db8a3 0x84787a4 0x846e851 0x836d12f 0x834cd1c 0x8349ba5 0x10a3177 0x8349961
|
||||
1: 1048576 [ 1: 1048576] @ 0x87d92e8 0x87d9213 0x87d9178 0x87d94d3 0x87da9da 0x8a364ff 0x8a437e7 0x8ab7d23 0x8ab7da9 0x8ac7454 0x8348465 0x10a3161 0x8349961
|
||||
[...]
|
||||
</pre>
|
||||
|
||||
|
||||
<h2> <A NAME="profile"><code><b>/pprof/profile</b></code></A> </h2>
|
||||
|
||||
<p><code>pprof</code> asks for the url
|
||||
<code>/pprof/profile?seconds=XX</code> to get cpu-profiling
|
||||
information. The actual url is controlled via the variable
|
||||
<code>PROFILE_PAGE</code> in the <code>pprof</code> script, so you can
|
||||
change it if you'd like.</p>
|
||||
|
||||
<p>The server should respond by calling
|
||||
<code>ProfilerStart(filename)</code>, continuing to do its work, and
|
||||
then, XX seconds later, calling <code>ProfilerStop()</code>. (These
|
||||
functions are declared in <code>gperftools/profiler.h</code>.) The
|
||||
application is responsible for picking a unique filename for
|
||||
<code>ProfilerStart()</code>. After calling
|
||||
<code>ProfilerStop()</code>, the server should read the contents of
|
||||
<code>filename</code> and send them back as an HTTP response to
|
||||
<code>pprof</code>.</p>
|
||||
|
||||
<p>Obviously, to get useful profile information the application must
|
||||
continue to run in the XX seconds that the profiler is running. Thus,
|
||||
the profile start-stop calls should be done in a separate thread, or
|
||||
be otherwise non-blocking.</p>
|
||||
|
||||
<p>The profiler output file is binary, but near the end of it, it
|
||||
should have lines of text somewhat like this:</p>
|
||||
<pre>
|
||||
01016000-01017000 rw-p 00015000 03:01 59314 /lib/ld-2.2.2.so
|
||||
</pre>
|
||||
|
||||
<h2> <code><b>/pprof/pmuprofile</b></code> </h2>
|
||||
|
||||
<code>pprof</code> asks for a url of the form
|
||||
<code>/pprof/pmuprofile?event=hw_event:unit_mask&period=nnn&seconds=xxx</code>
|
||||
to get cpu-profiling information. The actual url is controlled via the variable
|
||||
<code>PMUPROFILE_PAGE</code> in the <code>pprof</code> script, so you can
|
||||
change it if you'd like.</p>
|
||||
|
||||
<p>
|
||||
This is similar to pprof, but is meant to be used with your CPU's hardware
|
||||
performance counters. The server could be implemented on top of a library
|
||||
such as <a href="http://perfmon2.sourceforge.net/">
|
||||
<code>libpfm</code></a>. It should collect a sample every nnn occurrences
|
||||
of the event and stop the sampling after xxx seconds. Much of the code
|
||||
for <code>/pprof/profile</code> can be reused for this purpose.
|
||||
</p>
|
||||
|
||||
<p>The server side routines (the equivalent of
|
||||
ProfilerStart/ProfilerStart) are not available as part of perftools,
|
||||
so this URL is unlikely to be that useful.</p>
|
||||
|
||||
<h2> <code><b>/pprof/contention</b></code> </h2>
|
||||
|
||||
<p>This is intended to be able to profile (thread) lock contention in
|
||||
addition to CPU and memory use. It's not yet usable.</p>
|
||||
|
||||
|
||||
<h2> <code><b>/pprof/cmdline</b></code> </h2>
|
||||
|
||||
<p><code>pprof</code> asks for the url <code>/pprof/cmdline</code> to
|
||||
figure out what application it's profiling. The actual url is
|
||||
controlled via the variable <code>PROGRAM_NAME_PAGE</code> in the
|
||||
<code>pprof</code> script, so you can change it if you'd like.</p>
|
||||
|
||||
<p>The server should respond by reading the contents of
|
||||
<code>/proc/self/cmdline</code>, converting all internal NUL (\0)
|
||||
characters to newlines, and sending the result back as an HTTP
|
||||
response to <code>pprof</code>.</p>
|
||||
|
||||
<p>Here's an example return value:<p>
|
||||
<pre>
|
||||
/root/server/custom_webserver
|
||||
80
|
||||
--configfile=/root/server/ws.config
|
||||
</pre>
|
||||
|
||||
|
||||
<h2> <code><b>/pprof/symbol</b></code> </h2>
|
||||
|
||||
<p><code>pprof</code> asks for the url <code>/pprof/symbol</code> to
|
||||
map from hex addresses to variable names. The actual url is
|
||||
controlled via the variable <code>SYMBOL_PAGE</code> in the
|
||||
<code>pprof</code> script, so you can change it if you'd like.</p>
|
||||
|
||||
<p>When the server receives a GET request for
|
||||
<code>/pprof/symbol</code>, it should return a line formatted like
|
||||
so:</p>
|
||||
<pre>
|
||||
num_symbols: ###
|
||||
</pre>
|
||||
<p>where <code>###</code> is the number of symbols found in the
|
||||
binary. (For now, the only important distinction is whether the value
|
||||
is 0, which it is for executables that lack debug information, or
|
||||
not-0).</p>
|
||||
|
||||
<p>This is perhaps the hardest request to write code for, because in
|
||||
addition to the GET request for this url, the server must accept POST
|
||||
requests. This means that after the HTTP headers, pprof will pass in
|
||||
a list of hex addresses connected by <code>+</code>, like so:</p>
|
||||
<pre>
|
||||
curl -d '0x0824d061+0x0824d1cf' http://remote_host:80/pprof/symbol
|
||||
</pre>
|
||||
|
||||
<p>The server should read the POST data, which will be in one line,
|
||||
and for each hex value, should write one line of output to the output
|
||||
stream, like so:</p>
|
||||
<pre>
|
||||
<hex address><tab><function name>
|
||||
</pre>
|
||||
<p>For instance:</p>
|
||||
<pre>
|
||||
0x08b2dabd _Update
|
||||
</pre>
|
||||
|
||||
<p>The other reason this is the most difficult request to implement,
|
||||
is that the application will have to figure out for itself how to map
|
||||
from address to function name. One possibility is to run <code>nm -C
|
||||
-n <program name></code> to get the mappings at
|
||||
program-compile-time. Another, at least on Linux, is to call out to
|
||||
addr2line for every <code>pprof/symbol</code> call, for instance
|
||||
<code>addr2line -Cfse /proc/<getpid>/exe 0x12345678 0x876543210</code>
|
||||
(presumably with some caching!)</p>
|
||||
|
||||
<p><code>pprof</code> itself does just this for local profiles (not
|
||||
ones that talk to remote servers); look at the subroutine
|
||||
<code>GetProcedureBoundaries</code>.</p>
|
||||
|
||||
|
||||
<hr>
|
||||
Last modified: Mon Jun 12 21:30:14 PDT 2006
|
||||
</body>
|
||||
</html>
|
22
trunk/3rdparty/gperftools-2-fit/docs/spanmap.dot
vendored
Normal file
|
@ -0,0 +1,22 @@
|
|||
digraph SpanMap {
|
||||
node [shape=box, width=0.3, height=0.3]
|
||||
nodesep=.05
|
||||
|
||||
map [shape=record, width=6, label="<f0>|<f1>|<f2>|<f3>|<f4>|<f5>|<f6>|<f7>|<f8>|<f9>|<f10>"]
|
||||
S0 [label="a"]
|
||||
S1 [label="b"]
|
||||
S2 [label="c"]
|
||||
S3 [label="d"]
|
||||
map:f0 -> S0
|
||||
map:f1 -> S0
|
||||
map:f2 -> S1
|
||||
map:f3 -> S2
|
||||
map:f4 -> S2
|
||||
map:f5 -> S2
|
||||
map:f6 -> S2
|
||||
map:f7 -> S2
|
||||
map:f8 -> S3
|
||||
map:f9 -> S3
|
||||
map:f10 -> S3
|
||||
|
||||
}
|
BIN
trunk/3rdparty/gperftools-2-fit/docs/spanmap.gif
vendored
Normal file
After Width: | Height: | Size: 8.3 KiB |
480
trunk/3rdparty/gperftools-2-fit/docs/t-test1.times.txt
vendored
Normal file
|
@ -0,0 +1,480 @@
|
|||
time.1.ptmalloc.64:0.56 user 0.02 system 0.57 elapsed 100% CPU
|
||||
time.1.tcmalloc.64:0.38 user 0.02 system 0.40 elapsed 98% CPU
|
||||
time.1.ptmalloc.128:0.61 user 0.01 system 0.61 elapsed 101% CPU
|
||||
time.1.tcmalloc.128:0.35 user 0.00 system 0.35 elapsed 99% CPU
|
||||
time.1.ptmalloc.256:0.59 user 0.01 system 0.60 elapsed 100% CPU
|
||||
time.1.tcmalloc.256:0.27 user 0.02 system 0.28 elapsed 102% CPU
|
||||
time.1.ptmalloc.512:0.57 user 0.00 system 0.57 elapsed 100% CPU
|
||||
time.1.tcmalloc.512:0.25 user 0.01 system 0.25 elapsed 101% CPU
|
||||
time.1.ptmalloc.1024:0.52 user 0.00 system 0.52 elapsed 99% CPU
|
||||
time.1.tcmalloc.1024:0.22 user 0.02 system 0.24 elapsed 97% CPU
|
||||
time.1.ptmalloc.2048:0.47 user 0.00 system 0.47 elapsed 99% CPU
|
||||
time.1.tcmalloc.2048:0.22 user 0.02 system 0.25 elapsed 95% CPU
|
||||
time.1.ptmalloc.4096:0.48 user 0.01 system 0.48 elapsed 100% CPU
|
||||
time.1.tcmalloc.4096:0.25 user 0.01 system 0.25 elapsed 100% CPU
|
||||
time.1.ptmalloc.8192:0.49 user 0.02 system 0.49 elapsed 102% CPU
|
||||
time.1.tcmalloc.8192:0.27 user 0.02 system 0.28 elapsed 101% CPU
|
||||
time.1.ptmalloc.16384:0.51 user 0.04 system 0.55 elapsed 99% CPU
|
||||
time.1.tcmalloc.16384:0.35 user 0.02 system 0.37 elapsed 100% CPU
|
||||
time.1.ptmalloc.32768:0.53 user 0.14 system 0.66 elapsed 100% CPU
|
||||
time.1.tcmalloc.32768:0.67 user 0.02 system 0.69 elapsed 99% CPU
|
||||
time.1.ptmalloc.65536:0.68 user 0.31 system 0.98 elapsed 100% CPU
|
||||
time.1.tcmalloc.65536:0.71 user 0.01 system 0.72 elapsed 99% CPU
|
||||
time.1.ptmalloc.131072:0.90 user 0.72 system 1.62 elapsed 99% CPU
|
||||
time.1.tcmalloc.131072:0.94 user 0.03 system 0.97 elapsed 99% CPU
|
||||
time.2.ptmalloc.64:1.05 user 0.00 system 0.53 elapsed 196% CPU
|
||||
time.2.tcmalloc.64:0.66 user 0.03 system 0.37 elapsed 185% CPU
|
||||
time.2.ptmalloc.128:1.77 user 0.01 system 0.89 elapsed 198% CPU
|
||||
time.2.tcmalloc.128:0.53 user 0.01 system 0.29 elapsed 184% CPU
|
||||
time.2.ptmalloc.256:1.14 user 0.01 system 0.62 elapsed 182% CPU
|
||||
time.2.tcmalloc.256:0.45 user 0.02 system 0.26 elapsed 180% CPU
|
||||
time.2.ptmalloc.512:1.26 user 0.40 system 1.79 elapsed 92% CPU
|
||||
time.2.tcmalloc.512:0.43 user 0.02 system 0.27 elapsed 166% CPU
|
||||
time.2.ptmalloc.1024:0.98 user 0.03 system 0.56 elapsed 179% CPU
|
||||
time.2.tcmalloc.1024:0.44 user 0.02 system 0.34 elapsed 134% CPU
|
||||
time.2.ptmalloc.2048:0.87 user 0.02 system 0.44 elapsed 199% CPU
|
||||
time.2.tcmalloc.2048:0.49 user 0.02 system 0.34 elapsed 148% CPU
|
||||
time.2.ptmalloc.4096:0.92 user 0.03 system 0.48 elapsed 196% CPU
|
||||
time.2.tcmalloc.4096:0.50 user 0.02 system 0.49 elapsed 105% CPU
|
||||
time.2.ptmalloc.8192:1.05 user 0.04 system 0.55 elapsed 196% CPU
|
||||
time.2.tcmalloc.8192:0.59 user 0.01 system 0.51 elapsed 116% CPU
|
||||
time.2.ptmalloc.16384:1.30 user 0.14 system 0.72 elapsed 198% CPU
|
||||
time.2.tcmalloc.16384:0.63 user 0.03 system 0.68 elapsed 96% CPU
|
||||
time.2.ptmalloc.32768:1.33 user 0.56 system 1.00 elapsed 189% CPU
|
||||
time.2.tcmalloc.32768:1.16 user 0.01 system 1.17 elapsed 99% CPU
|
||||
time.2.ptmalloc.65536:1.86 user 1.79 system 2.01 elapsed 181% CPU
|
||||
time.2.tcmalloc.65536:1.35 user 0.01 system 1.35 elapsed 100% CPU
|
||||
time.2.ptmalloc.131072:2.61 user 5.19 system 4.81 elapsed 162% CPU
|
||||
time.2.tcmalloc.131072:1.86 user 0.04 system 1.90 elapsed 100% CPU
|
||||
time.3.ptmalloc.64:1.79 user 0.03 system 0.67 elapsed 268% CPU
|
||||
time.3.tcmalloc.64:1.58 user 0.04 system 0.62 elapsed 260% CPU
|
||||
time.3.ptmalloc.128:2.77 user 1.34 system 3.07 elapsed 133% CPU
|
||||
time.3.tcmalloc.128:1.19 user 0.01 system 0.50 elapsed 236% CPU
|
||||
time.3.ptmalloc.256:2.14 user 0.02 system 0.85 elapsed 252% CPU
|
||||
time.3.tcmalloc.256:0.96 user 0.01 system 0.41 elapsed 236% CPU
|
||||
time.3.ptmalloc.512:3.37 user 1.31 system 3.33 elapsed 140% CPU
|
||||
time.3.tcmalloc.512:0.93 user 0.04 system 0.39 elapsed 243% CPU
|
||||
time.3.ptmalloc.1024:1.66 user 0.01 system 0.64 elapsed 260% CPU
|
||||
time.3.tcmalloc.1024:0.81 user 0.02 system 0.44 elapsed 187% CPU
|
||||
time.3.ptmalloc.2048:2.07 user 0.01 system 0.82 elapsed 252% CPU
|
||||
time.3.tcmalloc.2048:1.10 user 0.04 system 0.59 elapsed 191% CPU
|
||||
time.3.ptmalloc.4096:2.01 user 0.03 system 0.79 elapsed 258% CPU
|
||||
time.3.tcmalloc.4096:0.87 user 0.03 system 0.65 elapsed 137% CPU
|
||||
time.3.ptmalloc.8192:2.22 user 0.11 system 0.83 elapsed 280% CPU
|
||||
time.3.tcmalloc.8192:0.96 user 0.06 system 0.75 elapsed 135% CPU
|
||||
time.3.ptmalloc.16384:2.56 user 0.47 system 1.02 elapsed 295% CPU
|
||||
time.3.tcmalloc.16384:0.99 user 0.04 system 1.03 elapsed 99% CPU
|
||||
time.3.ptmalloc.32768:3.29 user 1.75 system 1.96 elapsed 256% CPU
|
||||
time.3.tcmalloc.32768:1.67 user 0.02 system 1.69 elapsed 99% CPU
|
||||
time.3.ptmalloc.65536:4.04 user 6.62 system 4.92 elapsed 216% CPU
|
||||
time.3.tcmalloc.65536:1.91 user 0.02 system 1.98 elapsed 97% CPU
|
||||
time.3.ptmalloc.131072:5.55 user 17.86 system 12.44 elapsed 188% CPU
|
||||
time.3.tcmalloc.131072:2.78 user 0.02 system 2.82 elapsed 99% CPU
|
||||
time.4.ptmalloc.64:3.42 user 1.36 system 3.20 elapsed 149% CPU
|
||||
time.4.tcmalloc.64:2.42 user 0.02 system 0.71 elapsed 341% CPU
|
||||
time.4.ptmalloc.128:3.98 user 1.79 system 3.89 elapsed 148% CPU
|
||||
time.4.tcmalloc.128:1.87 user 0.02 system 0.58 elapsed 325% CPU
|
||||
time.4.ptmalloc.256:4.06 user 2.14 system 4.12 elapsed 150% CPU
|
||||
time.4.tcmalloc.256:1.69 user 0.02 system 0.51 elapsed 331% CPU
|
||||
time.4.ptmalloc.512:4.48 user 2.15 system 4.39 elapsed 150% CPU
|
||||
time.4.tcmalloc.512:1.62 user 0.03 system 0.52 elapsed 314% CPU
|
||||
time.4.ptmalloc.1024:3.18 user 0.03 system 0.84 elapsed 381% CPU
|
||||
time.4.tcmalloc.1024:1.53 user 0.02 system 0.56 elapsed 274% CPU
|
||||
time.4.ptmalloc.2048:3.24 user 0.02 system 0.84 elapsed 384% CPU
|
||||
time.4.tcmalloc.2048:1.44 user 0.04 system 0.66 elapsed 221% CPU
|
||||
time.4.ptmalloc.4096:3.50 user 0.04 system 0.91 elapsed 389% CPU
|
||||
time.4.tcmalloc.4096:1.31 user 0.01 system 0.89 elapsed 148% CPU
|
||||
time.4.ptmalloc.8192:6.77 user 3.85 system 4.14 elapsed 256% CPU
|
||||
time.4.tcmalloc.8192:1.20 user 0.05 system 0.97 elapsed 127% CPU
|
||||
time.4.ptmalloc.16384:7.08 user 5.06 system 4.63 elapsed 262% CPU
|
||||
time.4.tcmalloc.16384:1.27 user 0.03 system 1.25 elapsed 103% CPU
|
||||
time.4.ptmalloc.32768:5.57 user 4.22 system 3.31 elapsed 295% CPU
|
||||
time.4.tcmalloc.32768:2.17 user 0.03 system 2.25 elapsed 97% CPU
|
||||
time.4.ptmalloc.65536:6.11 user 15.05 system 9.19 elapsed 230% CPU
|
||||
time.4.tcmalloc.65536:2.51 user 0.02 system 2.57 elapsed 98% CPU
|
||||
time.4.ptmalloc.131072:7.58 user 33.15 system 21.28 elapsed 191% CPU
|
||||
time.4.tcmalloc.131072:3.57 user 0.07 system 3.66 elapsed 99% CPU
|
||||
time.5.ptmalloc.64:4.44 user 2.08 system 4.37 elapsed 148% CPU
|
||||
time.5.tcmalloc.64:2.87 user 0.02 system 0.79 elapsed 361% CPU
|
||||
time.5.ptmalloc.128:4.77 user 2.77 system 5.14 elapsed 146% CPU
|
||||
time.5.tcmalloc.128:2.65 user 0.03 system 0.72 elapsed 367% CPU
|
||||
time.5.ptmalloc.256:5.82 user 2.88 system 5.49 elapsed 158% CPU
|
||||
time.5.tcmalloc.256:2.33 user 0.01 system 0.66 elapsed 352% CPU
|
||||
time.5.ptmalloc.512:6.27 user 3.11 system 5.34 elapsed 175% CPU
|
||||
time.5.tcmalloc.512:2.14 user 0.03 system 0.70 elapsed 307% CPU
|
||||
time.5.ptmalloc.1024:6.82 user 3.18 system 5.23 elapsed 191% CPU
|
||||
time.5.tcmalloc.1024:2.20 user 0.02 system 0.70 elapsed 313% CPU
|
||||
time.5.ptmalloc.2048:6.57 user 3.46 system 5.22 elapsed 192% CPU
|
||||
time.5.tcmalloc.2048:2.15 user 0.03 system 0.82 elapsed 264% CPU
|
||||
time.5.ptmalloc.4096:8.75 user 5.09 system 5.26 elapsed 263% CPU
|
||||
time.5.tcmalloc.4096:1.68 user 0.03 system 1.08 elapsed 158% CPU
|
||||
time.5.ptmalloc.8192:4.48 user 0.61 system 1.51 elapsed 335% CPU
|
||||
time.5.tcmalloc.8192:1.47 user 0.07 system 1.18 elapsed 129% CPU
|
||||
time.5.ptmalloc.16384:5.71 user 1.98 system 2.14 elapsed 358% CPU
|
||||
time.5.tcmalloc.16384:1.58 user 0.03 system 1.52 elapsed 105% CPU
|
||||
time.5.ptmalloc.32768:7.19 user 7.81 system 5.53 elapsed 270% CPU
|
||||
time.5.tcmalloc.32768:2.63 user 0.05 system 2.72 elapsed 98% CPU
|
||||
time.5.ptmalloc.65536:8.45 user 23.51 system 14.30 elapsed 223% CPU
|
||||
time.5.tcmalloc.65536:3.12 user 0.05 system 3.21 elapsed 98% CPU
|
||||
time.5.ptmalloc.131072:10.22 user 43.63 system 27.84 elapsed 193% CPU
|
||||
time.5.tcmalloc.131072:4.42 user 0.07 system 4.51 elapsed 99% CPU
|
||||
time.6.ptmalloc.64:5.57 user 2.56 system 5.08 elapsed 159% CPU
|
||||
time.6.tcmalloc.64:3.20 user 0.01 system 0.89 elapsed 360% CPU
|
||||
time.6.ptmalloc.128:5.98 user 3.52 system 5.71 elapsed 166% CPU
|
||||
time.6.tcmalloc.128:2.76 user 0.02 system 0.78 elapsed 355% CPU
|
||||
time.6.ptmalloc.256:4.61 user 0.02 system 1.19 elapsed 389% CPU
|
||||
time.6.tcmalloc.256:2.65 user 0.02 system 0.74 elapsed 356% CPU
|
||||
time.6.ptmalloc.512:8.28 user 3.88 system 6.61 elapsed 183% CPU
|
||||
time.6.tcmalloc.512:2.60 user 0.02 system 0.72 elapsed 362% CPU
|
||||
time.6.ptmalloc.1024:4.75 user 0.00 system 1.22 elapsed 387% CPU
|
||||
time.6.tcmalloc.1024:2.56 user 0.02 system 0.79 elapsed 325% CPU
|
||||
time.6.ptmalloc.2048:8.90 user 4.59 system 6.15 elapsed 219% CPU
|
||||
time.6.tcmalloc.2048:2.37 user 0.06 system 0.96 elapsed 250% CPU
|
||||
time.6.ptmalloc.4096:11.41 user 7.02 system 6.31 elapsed 291% CPU
|
||||
time.6.tcmalloc.4096:1.82 user 0.03 system 1.19 elapsed 154% CPU
|
||||
time.6.ptmalloc.8192:11.64 user 8.25 system 5.97 elapsed 332% CPU
|
||||
time.6.tcmalloc.8192:1.83 user 0.07 system 1.38 elapsed 136% CPU
|
||||
time.6.ptmalloc.16384:7.44 user 2.98 system 3.01 elapsed 345% CPU
|
||||
time.6.tcmalloc.16384:1.83 user 0.08 system 1.80 elapsed 105% CPU
|
||||
time.6.ptmalloc.32768:8.69 user 12.35 system 8.04 elapsed 261% CPU
|
||||
time.6.tcmalloc.32768:3.14 user 0.06 system 3.24 elapsed 98% CPU
|
||||
time.6.ptmalloc.65536:10.52 user 35.43 system 20.75 elapsed 221% CPU
|
||||
time.6.tcmalloc.65536:3.62 user 0.03 system 3.72 elapsed 98% CPU
|
||||
time.6.ptmalloc.131072:11.74 user 59.00 system 36.93 elapsed 191% CPU
|
||||
time.6.tcmalloc.131072:5.33 user 0.04 system 5.42 elapsed 98% CPU
|
||||
time.7.ptmalloc.64:6.60 user 3.45 system 6.01 elapsed 167% CPU
|
||||
time.7.tcmalloc.64:3.50 user 0.04 system 0.94 elapsed 376% CPU
|
||||
time.7.ptmalloc.128:7.09 user 4.25 system 6.69 elapsed 169% CPU
|
||||
time.7.tcmalloc.128:3.13 user 0.03 system 0.84 elapsed 374% CPU
|
||||
time.7.ptmalloc.256:9.28 user 4.85 system 7.20 elapsed 196% CPU
|
||||
time.7.tcmalloc.256:3.06 user 0.02 system 0.82 elapsed 375% CPU
|
||||
time.7.ptmalloc.512:9.13 user 4.78 system 6.79 elapsed 204% CPU
|
||||
time.7.tcmalloc.512:2.99 user 0.03 system 0.83 elapsed 359% CPU
|
||||
time.7.ptmalloc.1024:10.85 user 6.41 system 7.52 elapsed 229% CPU
|
||||
time.7.tcmalloc.1024:3.05 user 0.04 system 0.89 elapsed 345% CPU
|
||||
time.7.ptmalloc.2048:5.65 user 0.08 system 1.47 elapsed 388% CPU
|
||||
time.7.tcmalloc.2048:3.01 user 0.01 system 0.98 elapsed 306% CPU
|
||||
time.7.ptmalloc.4096:6.09 user 0.08 system 1.58 elapsed 389% CPU
|
||||
time.7.tcmalloc.4096:2.25 user 0.03 system 1.32 elapsed 171% CPU
|
||||
time.7.ptmalloc.8192:6.73 user 0.85 system 1.99 elapsed 379% CPU
|
||||
time.7.tcmalloc.8192:2.22 user 0.08 system 1.61 elapsed 142% CPU
|
||||
time.7.ptmalloc.16384:8.87 user 4.66 system 4.04 elapsed 334% CPU
|
||||
time.7.tcmalloc.16384:2.07 user 0.07 system 2.07 elapsed 103% CPU
|
||||
time.7.ptmalloc.32768:10.61 user 17.85 system 11.22 elapsed 253% CPU
|
||||
time.7.tcmalloc.32768:3.68 user 0.06 system 3.79 elapsed 98% CPU
|
||||
time.7.ptmalloc.65536:13.05 user 45.97 system 27.28 elapsed 216% CPU
|
||||
time.7.tcmalloc.65536:4.16 user 0.07 system 4.31 elapsed 98% CPU
|
||||
time.7.ptmalloc.131072:13.22 user 62.67 system 41.33 elapsed 183% CPU
|
||||
time.7.tcmalloc.131072:6.10 user 0.06 system 6.25 elapsed 98% CPU
|
||||
time.8.ptmalloc.64:7.31 user 3.92 system 6.39 elapsed 175% CPU
|
||||
time.8.tcmalloc.64:4.00 user 0.01 system 1.04 elapsed 383% CPU
|
||||
time.8.ptmalloc.128:9.40 user 5.41 system 7.67 elapsed 192% CPU
|
||||
time.8.tcmalloc.128:3.61 user 0.02 system 0.94 elapsed 386% CPU
|
||||
time.8.ptmalloc.256:10.61 user 6.35 system 7.96 elapsed 212% CPU
|
||||
time.8.tcmalloc.256:3.30 user 0.02 system 0.99 elapsed 335% CPU
|
||||
time.8.ptmalloc.512:12.42 user 7.10 system 8.79 elapsed 221% CPU
|
||||
time.8.tcmalloc.512:3.35 user 0.04 system 0.94 elapsed 358% CPU
|
||||
time.8.ptmalloc.1024:13.63 user 8.54 system 8.95 elapsed 247% CPU
|
||||
time.8.tcmalloc.1024:3.44 user 0.02 system 0.96 elapsed 359% CPU
|
||||
time.8.ptmalloc.2048:6.45 user 0.03 system 1.67 elapsed 386% CPU
|
||||
time.8.tcmalloc.2048:3.55 user 0.05 system 1.09 elapsed 328% CPU
|
||||
time.8.ptmalloc.4096:6.83 user 0.26 system 1.80 elapsed 393% CPU
|
||||
time.8.tcmalloc.4096:2.78 user 0.06 system 1.53 elapsed 185% CPU
|
||||
time.8.ptmalloc.8192:7.59 user 1.29 system 2.36 elapsed 376% CPU
|
||||
time.8.tcmalloc.8192:2.57 user 0.07 system 1.84 elapsed 142% CPU
|
||||
time.8.ptmalloc.16384:10.15 user 6.20 system 5.20 elapsed 314% CPU
|
||||
time.8.tcmalloc.16384:2.40 user 0.05 system 2.42 elapsed 101% CPU
|
||||
time.8.ptmalloc.32768:11.82 user 24.48 system 14.60 elapsed 248% CPU
|
||||
time.8.tcmalloc.32768:4.37 user 0.05 system 4.47 elapsed 98% CPU
|
||||
time.8.ptmalloc.65536:15.41 user 58.94 system 34.42 elapsed 215% CPU
|
||||
time.8.tcmalloc.65536:4.90 user 0.04 system 4.96 elapsed 99% CPU
|
||||
time.8.ptmalloc.131072:16.07 user 82.93 system 52.51 elapsed 188% CPU
|
||||
time.8.tcmalloc.131072:7.13 user 0.04 system 7.19 elapsed 99% CPU
|
||||
time.9.ptmalloc.64:8.44 user 4.59 system 6.92 elapsed 188% CPU
|
||||
time.9.tcmalloc.64:4.00 user 0.02 system 1.05 elapsed 382% CPU
|
||||
time.9.ptmalloc.128:10.92 user 6.14 system 8.31 elapsed 205% CPU
|
||||
time.9.tcmalloc.128:3.88 user 0.02 system 1.01 elapsed 382% CPU
|
||||
time.9.ptmalloc.256:13.01 user 7.75 system 9.12 elapsed 227% CPU
|
||||
time.9.tcmalloc.256:3.89 user 0.01 system 1.00 elapsed 386% CPU
|
||||
time.9.ptmalloc.512:14.96 user 8.89 system 9.73 elapsed 244% CPU
|
||||
time.9.tcmalloc.512:3.80 user 0.03 system 1.01 elapsed 377% CPU
|
||||
time.9.ptmalloc.1024:15.42 user 10.20 system 9.80 elapsed 261% CPU
|
||||
time.9.tcmalloc.1024:3.86 user 0.03 system 1.19 elapsed 325% CPU
|
||||
time.9.ptmalloc.2048:7.24 user 0.02 system 1.87 elapsed 388% CPU
|
||||
time.9.tcmalloc.2048:3.98 user 0.05 system 1.26 elapsed 319% CPU
|
||||
time.9.ptmalloc.4096:7.96 user 0.18 system 2.06 elapsed 394% CPU
|
||||
time.9.tcmalloc.4096:3.27 user 0.04 system 1.69 elapsed 195% CPU
|
||||
time.9.ptmalloc.8192:9.00 user 1.63 system 2.79 elapsed 380% CPU
|
||||
time.9.tcmalloc.8192:3.00 user 0.06 system 2.05 elapsed 148% CPU
|
||||
time.9.ptmalloc.16384:12.07 user 8.13 system 6.55 elapsed 308% CPU
|
||||
time.9.tcmalloc.16384:2.85 user 0.05 system 2.75 elapsed 105% CPU
|
||||
time.9.ptmalloc.32768:13.99 user 29.65 system 18.02 elapsed 242% CPU
|
||||
time.9.tcmalloc.32768:4.98 user 0.06 system 5.13 elapsed 98% CPU
|
||||
time.9.ptmalloc.65536:16.89 user 70.42 system 42.11 elapsed 207% CPU
|
||||
time.9.tcmalloc.65536:5.55 user 0.04 system 5.65 elapsed 98% CPU
|
||||
time.9.ptmalloc.131072:18.53 user 94.11 system 61.17 elapsed 184% CPU
|
||||
time.9.tcmalloc.131072:8.06 user 0.04 system 8.16 elapsed 99% CPU
|
||||
time.10.ptmalloc.64:9.81 user 5.70 system 7.42 elapsed 208% CPU
|
||||
time.10.tcmalloc.64:4.43 user 0.03 system 1.20 elapsed 370% CPU
|
||||
time.10.ptmalloc.128:12.69 user 7.81 system 9.02 elapsed 227% CPU
|
||||
time.10.tcmalloc.128:4.27 user 0.02 system 1.13 elapsed 378% CPU
|
||||
time.10.ptmalloc.256:15.04 user 9.53 system 9.92 elapsed 247% CPU
|
||||
time.10.tcmalloc.256:4.23 user 0.02 system 1.09 elapsed 388% CPU
|
||||
time.10.ptmalloc.512:17.30 user 10.46 system 10.61 elapsed 261% CPU
|
||||
time.10.tcmalloc.512:4.14 user 0.05 system 1.10 elapsed 379% CPU
|
||||
time.10.ptmalloc.1024:16.96 user 9.38 system 9.30 elapsed 283% CPU
|
||||
time.10.tcmalloc.1024:4.27 user 0.06 system 1.18 elapsed 366% CPU
|
||||
time.10.ptmalloc.2048:8.07 user 0.03 system 2.06 elapsed 393% CPU
|
||||
time.10.tcmalloc.2048:4.49 user 0.07 system 1.33 elapsed 342% CPU
|
||||
time.10.ptmalloc.4096:8.66 user 0.25 system 2.25 elapsed 394% CPU
|
||||
time.10.tcmalloc.4096:3.61 user 0.05 system 1.78 elapsed 205% CPU
|
||||
time.10.ptmalloc.8192:21.52 user 17.43 system 10.41 elapsed 374% CPU
|
||||
time.10.tcmalloc.8192:3.59 user 0.10 system 2.33 elapsed 158% CPU
|
||||
time.10.ptmalloc.16384:20.55 user 24.85 system 12.55 elapsed 361% CPU
|
||||
time.10.tcmalloc.16384:3.29 user 0.04 system 3.22 elapsed 103% CPU
|
||||
time.10.ptmalloc.32768:15.23 user 38.13 system 22.49 elapsed 237% CPU
|
||||
time.10.tcmalloc.32768:5.62 user 0.05 system 5.72 elapsed 99% CPU
|
||||
time.10.ptmalloc.65536:19.80 user 85.42 system 49.98 elapsed 210% CPU
|
||||
time.10.tcmalloc.65536:6.23 user 0.09 system 6.36 elapsed 99% CPU
|
||||
time.10.ptmalloc.131072:20.91 user 106.97 system 69.08 elapsed 185% CPU
|
||||
time.10.tcmalloc.131072:8.94 user 0.09 system 9.09 elapsed 99% CPU
|
||||
time.11.ptmalloc.64:10.82 user 6.34 system 7.92 elapsed 216% CPU
|
||||
time.11.tcmalloc.64:4.80 user 0.03 system 1.24 elapsed 387% CPU
|
||||
time.11.ptmalloc.128:14.58 user 8.61 system 9.81 elapsed 236% CPU
|
||||
time.11.tcmalloc.128:4.65 user 0.03 system 1.21 elapsed 384% CPU
|
||||
time.11.ptmalloc.256:17.38 user 10.98 system 10.75 elapsed 263% CPU
|
||||
time.11.tcmalloc.256:4.51 user 0.03 system 1.18 elapsed 384% CPU
|
||||
time.11.ptmalloc.512:19.18 user 11.71 system 10.95 elapsed 282% CPU
|
||||
time.11.tcmalloc.512:4.57 user 0.02 system 1.19 elapsed 384% CPU
|
||||
time.11.ptmalloc.1024:19.94 user 12.41 system 10.48 elapsed 308% CPU
|
||||
time.11.tcmalloc.1024:4.71 user 0.05 system 1.29 elapsed 367% CPU
|
||||
time.11.ptmalloc.2048:8.70 user 0.04 system 2.35 elapsed 371% CPU
|
||||
time.11.tcmalloc.2048:4.97 user 0.07 system 1.43 elapsed 350% CPU
|
||||
time.11.ptmalloc.4096:22.47 user 18.43 system 10.82 elapsed 377% CPU
|
||||
time.11.tcmalloc.4096:4.22 user 0.03 system 1.91 elapsed 221% CPU
|
||||
time.11.ptmalloc.8192:11.61 user 2.38 system 3.73 elapsed 374% CPU
|
||||
time.11.tcmalloc.8192:3.74 user 0.09 system 2.46 elapsed 155% CPU
|
||||
time.11.ptmalloc.16384:14.13 user 13.38 system 9.60 elapsed 286% CPU
|
||||
time.11.tcmalloc.16384:3.61 user 0.03 system 3.63 elapsed 100% CPU
|
||||
time.11.ptmalloc.32768:17.92 user 43.84 system 26.74 elapsed 230% CPU
|
||||
time.11.tcmalloc.32768:6.31 user 0.03 system 6.45 elapsed 98% CPU
|
||||
time.11.ptmalloc.65536:22.40 user 96.38 system 58.30 elapsed 203% CPU
|
||||
time.11.tcmalloc.65536:6.92 user 0.12 system 6.98 elapsed 100% CPU
|
||||
time.11.ptmalloc.131072:21.03 user 108.04 system 72.78 elapsed 177% CPU
|
||||
time.11.tcmalloc.131072:9.79 user 0.08 system 9.94 elapsed 99% CPU
|
||||
time.12.ptmalloc.64:12.23 user 7.16 system 8.38 elapsed 231% CPU
|
||||
time.12.tcmalloc.64:5.21 user 0.05 system 1.41 elapsed 371% CPU
|
||||
time.12.ptmalloc.128:16.97 user 10.19 system 10.47 elapsed 259% CPU
|
||||
time.12.tcmalloc.128:5.10 user 0.02 system 1.31 elapsed 390% CPU
|
||||
time.12.ptmalloc.256:19.99 user 12.10 system 11.57 elapsed 277% CPU
|
||||
time.12.tcmalloc.256:5.01 user 0.03 system 1.29 elapsed 390% CPU
|
||||
time.12.ptmalloc.512:21.85 user 12.66 system 11.46 elapsed 300% CPU
|
||||
time.12.tcmalloc.512:5.05 user 0.00 system 1.32 elapsed 379% CPU
|
||||
time.12.ptmalloc.1024:9.40 user 0.04 system 2.40 elapsed 393% CPU
|
||||
time.12.tcmalloc.1024:5.14 user 0.02 system 1.39 elapsed 369% CPU
|
||||
time.12.ptmalloc.2048:9.72 user 0.04 system 2.49 elapsed 391% CPU
|
||||
time.12.tcmalloc.2048:5.74 user 0.05 system 1.62 elapsed 355% CPU
|
||||
time.12.ptmalloc.4096:10.64 user 0.20 system 2.75 elapsed 393% CPU
|
||||
time.12.tcmalloc.4096:4.45 user 0.03 system 2.04 elapsed 218% CPU
|
||||
time.12.ptmalloc.8192:12.66 user 3.30 system 4.30 elapsed 371% CPU
|
||||
time.12.tcmalloc.8192:4.21 user 0.13 system 2.65 elapsed 163% CPU
|
||||
time.12.ptmalloc.16384:15.73 user 15.68 system 11.14 elapsed 281% CPU
|
||||
time.12.tcmalloc.16384:4.17 user 0.06 system 4.10 elapsed 102% CPU
|
||||
time.12.ptmalloc.32768:19.45 user 56.00 system 32.74 elapsed 230% CPU
|
||||
time.12.tcmalloc.32768:6.96 user 0.08 system 7.14 elapsed 98% CPU
|
||||
time.12.ptmalloc.65536:23.33 user 110.45 system 65.06 elapsed 205% CPU
|
||||
time.12.tcmalloc.65536:7.77 user 0.15 system 7.72 elapsed 102% CPU
|
||||
time.12.ptmalloc.131072:24.03 user 124.74 system 82.94 elapsed 179% CPU
|
||||
time.12.tcmalloc.131072:10.81 user 0.06 system 10.94 elapsed 99% CPU
|
||||
time.13.ptmalloc.64:14.08 user 7.60 system 8.85 elapsed 244% CPU
|
||||
time.13.tcmalloc.64:5.51 user 0.01 system 1.47 elapsed 375% CPU
|
||||
time.13.ptmalloc.128:18.20 user 10.98 system 10.99 elapsed 265% CPU
|
||||
time.13.tcmalloc.128:5.34 user 0.01 system 1.39 elapsed 382% CPU
|
||||
time.13.ptmalloc.256:21.48 user 13.94 system 12.25 elapsed 289% CPU
|
||||
time.13.tcmalloc.256:5.33 user 0.01 system 1.39 elapsed 381% CPU
|
||||
time.13.ptmalloc.512:24.22 user 14.84 system 12.97 elapsed 301% CPU
|
||||
time.13.tcmalloc.512:5.49 user 0.02 system 1.41 elapsed 389% CPU
|
||||
time.13.ptmalloc.1024:25.26 user 17.03 system 12.85 elapsed 328% CPU
|
||||
time.13.tcmalloc.1024:5.65 user 0.04 system 1.50 elapsed 378% CPU
|
||||
time.13.ptmalloc.2048:10.41 user 0.03 system 2.69 elapsed 387% CPU
|
||||
time.13.tcmalloc.2048:5.93 user 0.10 system 1.77 elapsed 339% CPU
|
||||
time.13.ptmalloc.4096:11.37 user 0.52 system 3.04 elapsed 391% CPU
|
||||
time.13.tcmalloc.4096:5.08 user 0.11 system 2.22 elapsed 233% CPU
|
||||
time.13.ptmalloc.8192:21.76 user 18.54 system 10.58 elapsed 380% CPU
|
||||
time.13.tcmalloc.8192:5.04 user 0.16 system 2.93 elapsed 177% CPU
|
||||
time.13.ptmalloc.16384:26.35 user 34.47 system 17.01 elapsed 357% CPU
|
||||
time.13.tcmalloc.16384:4.66 user 0.04 system 4.66 elapsed 100% CPU
|
||||
time.13.ptmalloc.32768:21.41 user 63.59 system 38.14 elapsed 222% CPU
|
||||
time.13.tcmalloc.32768:7.71 user 0.03 system 7.83 elapsed 98% CPU
|
||||
time.13.ptmalloc.65536:24.99 user 120.80 system 71.59 elapsed 203% CPU
|
||||
time.13.tcmalloc.65536:8.87 user 0.64 system 8.37 elapsed 113% CPU
|
||||
time.13.ptmalloc.131072:25.97 user 142.27 system 96.00 elapsed 175% CPU
|
||||
time.13.tcmalloc.131072:11.48 user 0.06 system 11.67 elapsed 98% CPU
|
||||
time.14.ptmalloc.64:15.01 user 9.11 system 9.41 elapsed 256% CPU
|
||||
time.14.tcmalloc.64:5.98 user 0.02 system 1.58 elapsed 378% CPU
|
||||
time.14.ptmalloc.128:20.34 user 12.72 system 11.62 elapsed 284% CPU
|
||||
time.14.tcmalloc.128:5.88 user 0.04 system 1.51 elapsed 392% CPU
|
||||
time.14.ptmalloc.256:24.26 user 14.95 system 12.92 elapsed 303% CPU
|
||||
time.14.tcmalloc.256:5.72 user 0.02 system 1.50 elapsed 381% CPU
|
||||
time.14.ptmalloc.512:27.28 user 16.45 system 13.89 elapsed 314% CPU
|
||||
time.14.tcmalloc.512:5.99 user 0.02 system 1.54 elapsed 388% CPU
|
||||
time.14.ptmalloc.1024:25.84 user 16.99 system 12.61 elapsed 339% CPU
|
||||
time.14.tcmalloc.1024:5.94 user 0.06 system 1.59 elapsed 375% CPU
|
||||
time.14.ptmalloc.2048:11.96 user 0.01 system 3.12 elapsed 382% CPU
|
||||
time.14.tcmalloc.2048:6.39 user 0.07 system 1.79 elapsed 359% CPU
|
||||
time.14.ptmalloc.4096:20.19 user 11.77 system 8.26 elapsed 386% CPU
|
||||
time.14.tcmalloc.4096:5.65 user 0.05 system 2.32 elapsed 244% CPU
|
||||
time.14.ptmalloc.8192:22.01 user 16.39 system 9.89 elapsed 387% CPU
|
||||
time.14.tcmalloc.8192:5.44 user 0.11 system 3.07 elapsed 180% CPU
|
||||
time.14.ptmalloc.16384:18.15 user 22.40 system 15.02 elapsed 269% CPU
|
||||
time.14.tcmalloc.16384:5.29 user 0.08 system 5.34 elapsed 100% CPU
|
||||
time.14.ptmalloc.32768:24.29 user 72.07 system 42.63 elapsed 225% CPU
|
||||
time.14.tcmalloc.32768:8.47 user 0.02 system 8.62 elapsed 98% CPU
|
||||
time.14.ptmalloc.65536:27.63 user 130.56 system 78.64 elapsed 201% CPU
|
||||
time.14.tcmalloc.65536:9.85 user 1.61 system 9.04 elapsed 126% CPU
|
||||
time.14.ptmalloc.131072:28.87 user 146.38 system 100.54 elapsed 174% CPU
|
||||
time.14.tcmalloc.131072:12.46 user 0.11 system 12.71 elapsed 98% CPU
|
||||
time.15.ptmalloc.64:16.25 user 10.05 system 9.82 elapsed 267% CPU
|
||||
time.15.tcmalloc.64:6.30 user 0.02 system 1.64 elapsed 385% CPU
|
||||
time.15.ptmalloc.128:22.33 user 13.23 system 12.24 elapsed 290% CPU
|
||||
time.15.tcmalloc.128:6.08 user 0.03 system 1.59 elapsed 384% CPU
|
||||
time.15.ptmalloc.256:26.56 user 16.57 system 13.70 elapsed 314% CPU
|
||||
time.15.tcmalloc.256:6.14 user 0.03 system 1.61 elapsed 382% CPU
|
||||
time.15.ptmalloc.512:29.68 user 18.08 system 14.56 elapsed 327% CPU
|
||||
time.15.tcmalloc.512:6.12 user 0.04 system 1.68 elapsed 364% CPU
|
||||
time.15.ptmalloc.1024:17.07 user 6.22 system 6.26 elapsed 371% CPU
|
||||
time.15.tcmalloc.1024:6.38 user 0.02 system 1.75 elapsed 364% CPU
|
||||
time.15.ptmalloc.2048:26.64 user 17.25 system 11.51 elapsed 381% CPU
|
||||
time.15.tcmalloc.2048:6.77 user 0.18 system 1.92 elapsed 361% CPU
|
||||
time.15.ptmalloc.4096:13.21 user 0.74 system 3.57 elapsed 390% CPU
|
||||
time.15.tcmalloc.4096:6.03 user 0.09 system 2.36 elapsed 258% CPU
|
||||
time.15.ptmalloc.8192:22.92 user 17.51 system 10.50 elapsed 385% CPU
|
||||
time.15.tcmalloc.8192:5.96 user 0.12 system 3.36 elapsed 180% CPU
|
||||
time.15.ptmalloc.16384:19.37 user 24.87 system 16.69 elapsed 264% CPU
|
||||
time.15.tcmalloc.16384:5.88 user 0.07 system 5.84 elapsed 101% CPU
|
||||
time.15.ptmalloc.32768:25.43 user 82.30 system 48.98 elapsed 219% CPU
|
||||
time.15.tcmalloc.32768:9.11 user 0.05 system 9.30 elapsed 98% CPU
|
||||
time.15.ptmalloc.65536:29.31 user 140.07 system 83.78 elapsed 202% CPU
|
||||
time.15.tcmalloc.65536:8.51 user 1.59 system 9.75 elapsed 103% CPU
|
||||
time.15.ptmalloc.131072:30.22 user 163.15 system 109.50 elapsed 176% CPU
|
||||
time.15.tcmalloc.131072:13.35 user 0.10 system 13.54 elapsed 99% CPU
|
||||
time.16.ptmalloc.64:17.69 user 10.11 system 10.11 elapsed 274% CPU
|
||||
time.16.tcmalloc.64:6.63 user 0.04 system 1.72 elapsed 387% CPU
|
||||
time.16.ptmalloc.128:23.05 user 14.37 system 12.75 elapsed 293% CPU
|
||||
time.16.tcmalloc.128:6.61 user 0.02 system 1.71 elapsed 387% CPU
|
||||
time.16.ptmalloc.256:29.11 user 19.35 system 14.57 elapsed 332% CPU
|
||||
time.16.tcmalloc.256:6.62 user 0.03 system 1.73 elapsed 382% CPU
|
||||
time.16.ptmalloc.512:31.65 user 18.71 system 14.71 elapsed 342% CPU
|
||||
time.16.tcmalloc.512:6.63 user 0.04 system 1.73 elapsed 383% CPU
|
||||
time.16.ptmalloc.1024:31.99 user 21.22 system 14.87 elapsed 357% CPU
|
||||
time.16.tcmalloc.1024:6.81 user 0.04 system 1.79 elapsed 382% CPU
|
||||
time.16.ptmalloc.2048:30.35 user 21.36 system 13.30 elapsed 388% CPU
|
||||
time.16.tcmalloc.2048:6.91 user 0.50 system 2.01 elapsed 367% CPU
|
||||
time.16.ptmalloc.4096:18.85 user 7.18 system 6.61 elapsed 393% CPU
|
||||
time.16.tcmalloc.4096:6.70 user 0.10 system 2.62 elapsed 259% CPU
|
||||
time.16.ptmalloc.8192:22.19 user 14.30 system 9.37 elapsed 389% CPU
|
||||
time.16.tcmalloc.8192:6.18 user 0.19 system 3.58 elapsed 177% CPU
|
||||
time.16.ptmalloc.16384:31.22 user 46.78 system 22.92 elapsed 340% CPU
|
||||
time.16.tcmalloc.16384:6.79 user 0.07 system 6.86 elapsed 99% CPU
|
||||
time.16.ptmalloc.32768:27.31 user 87.32 system 52.00 elapsed 220% CPU
|
||||
time.16.tcmalloc.32768:9.85 user 0.06 system 10.07 elapsed 98% CPU
|
||||
time.16.ptmalloc.65536:32.83 user 160.62 system 95.67 elapsed 202% CPU
|
||||
time.16.tcmalloc.65536:10.18 user 0.09 system 10.41 elapsed 98% CPU
|
||||
time.16.ptmalloc.131072:31.99 user 173.41 system 115.98 elapsed 177% CPU
|
||||
time.16.tcmalloc.131072:14.52 user 0.05 system 14.67 elapsed 99% CPU
|
||||
time.17.ptmalloc.64:19.38 user 11.61 system 10.61 elapsed 291% CPU
|
||||
time.17.tcmalloc.64:7.11 user 0.02 system 1.84 elapsed 386% CPU
|
||||
time.17.ptmalloc.128:26.25 user 16.15 system 13.53 elapsed 313% CPU
|
||||
time.17.tcmalloc.128:6.97 user 0.02 system 1.78 elapsed 390% CPU
|
||||
time.17.ptmalloc.256:30.66 user 18.36 system 14.97 elapsed 327% CPU
|
||||
time.17.tcmalloc.256:6.94 user 0.04 system 1.80 elapsed 387% CPU
|
||||
time.17.ptmalloc.512:33.71 user 22.79 system 15.95 elapsed 354% CPU
|
||||
time.17.tcmalloc.512:7.00 user 0.02 system 1.83 elapsed 381% CPU
|
||||
time.17.ptmalloc.1024:33.49 user 22.47 system 15.00 elapsed 373% CPU
|
||||
time.17.tcmalloc.1024:7.20 user 0.03 system 1.90 elapsed 380% CPU
|
||||
time.17.ptmalloc.2048:23.87 user 11.92 system 9.26 elapsed 386% CPU
|
||||
time.17.tcmalloc.2048:6.01 user 1.83 system 2.15 elapsed 363% CPU
|
||||
time.17.ptmalloc.4096:14.69 user 0.95 system 3.98 elapsed 392% CPU
|
||||
time.17.tcmalloc.4096:7.25 user 0.10 system 2.62 elapsed 279% CPU
|
||||
time.17.ptmalloc.8192:22.44 user 13.52 system 9.39 elapsed 382% CPU
|
||||
time.17.tcmalloc.8192:7.21 user 0.24 system 3.95 elapsed 188% CPU
|
||||
time.17.ptmalloc.16384:23.33 user 33.67 system 21.89 elapsed 260% CPU
|
||||
time.17.tcmalloc.16384:7.28 user 0.06 system 7.10 elapsed 103% CPU
|
||||
time.17.ptmalloc.32768:29.35 user 103.11 system 60.36 elapsed 219% CPU
|
||||
time.17.tcmalloc.32768:10.53 user 0.07 system 10.71 elapsed 98% CPU
|
||||
time.17.ptmalloc.65536:33.21 user 170.89 system 100.84 elapsed 202% CPU
|
||||
time.17.tcmalloc.65536:10.85 user 0.05 system 11.04 elapsed 98% CPU
|
||||
time.17.ptmalloc.131072:34.98 user 182.87 system 122.05 elapsed 178% CPU
|
||||
time.17.tcmalloc.131072:15.27 user 0.09 system 15.49 elapsed 99% CPU
|
||||
time.18.ptmalloc.64:21.08 user 12.15 system 11.43 elapsed 290% CPU
|
||||
time.18.tcmalloc.64:7.45 user 0.03 system 1.95 elapsed 383% CPU
|
||||
time.18.ptmalloc.128:27.65 user 17.26 system 14.03 elapsed 320% CPU
|
||||
time.18.tcmalloc.128:7.46 user 0.03 system 1.92 elapsed 389% CPU
|
||||
time.18.ptmalloc.256:32.78 user 20.55 system 15.70 elapsed 339% CPU
|
||||
time.18.tcmalloc.256:7.31 user 0.02 system 1.88 elapsed 389% CPU
|
||||
time.18.ptmalloc.512:33.31 user 20.06 system 15.05 elapsed 354% CPU
|
||||
time.18.tcmalloc.512:7.33 user 0.02 system 1.91 elapsed 383% CPU
|
||||
time.18.ptmalloc.1024:35.46 user 24.83 system 16.30 elapsed 369% CPU
|
||||
time.18.tcmalloc.1024:7.60 user 0.06 system 2.05 elapsed 373% CPU
|
||||
time.18.ptmalloc.2048:19.98 user 6.80 system 6.76 elapsed 395% CPU
|
||||
time.18.tcmalloc.2048:6.89 user 1.29 system 2.28 elapsed 357% CPU
|
||||
time.18.ptmalloc.4096:15.99 user 0.93 system 4.32 elapsed 391% CPU
|
||||
time.18.tcmalloc.4096:7.70 user 0.10 system 2.77 elapsed 280% CPU
|
||||
time.18.ptmalloc.8192:23.51 user 14.84 system 9.97 elapsed 384% CPU
|
||||
time.18.tcmalloc.8192:8.16 user 0.27 system 4.25 elapsed 197% CPU
|
||||
time.18.ptmalloc.16384:35.79 user 52.41 system 26.47 elapsed 333% CPU
|
||||
time.18.tcmalloc.16384:7.81 user 0.07 system 7.61 elapsed 103% CPU
|
||||
time.18.ptmalloc.32768:33.17 user 116.07 system 68.64 elapsed 217% CPU
|
||||
time.18.tcmalloc.32768:11.34 user 0.13 system 11.57 elapsed 99% CPU
|
||||
time.18.ptmalloc.65536:35.91 user 177.82 system 106.75 elapsed 200% CPU
|
||||
time.18.tcmalloc.65536:11.54 user 0.06 system 11.74 elapsed 98% CPU
|
||||
time.18.ptmalloc.131072:36.38 user 187.18 system 126.91 elapsed 176% CPU
|
||||
time.18.tcmalloc.131072:16.34 user 0.05 system 16.43 elapsed 99% CPU
|
||||
time.19.ptmalloc.64:22.90 user 13.23 system 11.82 elapsed 305% CPU
|
||||
time.19.tcmalloc.64:7.81 user 0.02 system 2.01 elapsed 388% CPU
|
||||
time.19.ptmalloc.128:30.13 user 18.58 system 14.77 elapsed 329% CPU
|
||||
time.19.tcmalloc.128:7.74 user 0.02 system 2.01 elapsed 386% CPU
|
||||
time.19.ptmalloc.256:35.33 user 21.41 system 16.35 elapsed 347% CPU
|
||||
time.19.tcmalloc.256:7.79 user 0.04 system 2.04 elapsed 382% CPU
|
||||
time.19.ptmalloc.512:39.30 user 26.22 system 17.84 elapsed 367% CPU
|
||||
time.19.tcmalloc.512:7.80 user 0.06 system 2.05 elapsed 381% CPU
|
||||
time.19.ptmalloc.1024:35.70 user 23.90 system 15.66 elapsed 380% CPU
|
||||
time.19.tcmalloc.1024:8.08 user 0.06 system 2.16 elapsed 376% CPU
|
||||
time.19.ptmalloc.2048:18.33 user 3.28 system 5.47 elapsed 394% CPU
|
||||
time.19.tcmalloc.2048:8.71 user 0.05 system 2.40 elapsed 363% CPU
|
||||
time.19.ptmalloc.4096:16.94 user 0.89 system 4.64 elapsed 383% CPU
|
||||
time.19.tcmalloc.4096:8.21 user 0.07 system 2.85 elapsed 289% CPU
|
||||
time.19.ptmalloc.8192:25.61 user 17.15 system 11.33 elapsed 377% CPU
|
||||
time.19.tcmalloc.8192:8.79 user 0.30 system 4.58 elapsed 198% CPU
|
||||
time.19.ptmalloc.16384:27.11 user 46.66 system 29.67 elapsed 248% CPU
|
||||
time.19.tcmalloc.16384:8.64 user 0.05 system 8.58 elapsed 101% CPU
|
||||
time.19.ptmalloc.32768:33.80 user 117.69 system 70.65 elapsed 214% CPU
|
||||
time.19.tcmalloc.32768:11.88 user 0.07 system 12.04 elapsed 99% CPU
|
||||
time.19.ptmalloc.65536:36.90 user 180.21 system 109.01 elapsed 199% CPU
|
||||
time.19.tcmalloc.65536:12.17 user 0.07 system 12.40 elapsed 98% CPU
|
||||
time.19.ptmalloc.131072:38.50 user 195.15 system 132.81 elapsed 175% CPU
|
||||
time.19.tcmalloc.131072:17.44 user 0.10 system 17.65 elapsed 99% CPU
|
||||
time.20.ptmalloc.64:23.37 user 13.74 system 11.86 elapsed 312% CPU
|
||||
time.20.tcmalloc.64:8.18 user 0.02 system 2.10 elapsed 389% CPU
|
||||
time.20.ptmalloc.128:31.29 user 19.97 system 15.53 elapsed 329% CPU
|
||||
time.20.tcmalloc.128:8.03 user 0.02 system 2.12 elapsed 378% CPU
|
||||
time.20.ptmalloc.256:38.40 user 25.65 system 18.25 elapsed 350% CPU
|
||||
time.20.tcmalloc.256:8.05 user 0.05 system 2.12 elapsed 380% CPU
|
||||
time.20.ptmalloc.512:40.60 user 27.70 system 18.46 elapsed 369% CPU
|
||||
time.20.tcmalloc.512:8.22 user 0.08 system 2.20 elapsed 375% CPU
|
||||
time.20.ptmalloc.1024:40.02 user 28.52 system 17.56 elapsed 390% CPU
|
||||
time.20.tcmalloc.1024:8.50 user 0.07 system 2.19 elapsed 391% CPU
|
||||
time.20.ptmalloc.2048:16.13 user 0.23 system 4.23 elapsed 386% CPU
|
||||
time.20.tcmalloc.2048:8.98 user 0.03 system 2.45 elapsed 367% CPU
|
||||
time.20.ptmalloc.4096:17.14 user 0.87 system 4.60 elapsed 391% CPU
|
||||
time.20.tcmalloc.4096:8.93 user 0.20 system 2.97 elapsed 306% CPU
|
||||
time.20.ptmalloc.8192:25.24 user 17.16 system 11.14 elapsed 380% CPU
|
||||
time.20.tcmalloc.8192:9.78 user 0.30 system 5.14 elapsed 195% CPU
|
||||
time.20.ptmalloc.16384:39.93 user 60.36 system 30.24 elapsed 331% CPU
|
||||
time.20.tcmalloc.16384:9.57 user 0.09 system 9.43 elapsed 102% CPU
|
||||
time.20.ptmalloc.32768:36.44 user 130.23 system 76.79 elapsed 217% CPU
|
||||
time.20.tcmalloc.32768:12.71 user 0.09 system 12.97 elapsed 98% CPU
|
||||
time.20.ptmalloc.65536:39.79 user 202.09 system 120.34 elapsed 200% CPU
|
||||
time.20.tcmalloc.65536:12.93 user 0.06 system 13.15 elapsed 98% CPU
|
||||
time.20.ptmalloc.131072:41.91 user 202.76 system 138.51 elapsed 176% CPU
|
||||
time.20.tcmalloc.131072:18.23 user 0.07 system 18.42 elapsed 99% CPU
|
BIN
trunk/3rdparty/gperftools-2-fit/docs/tcmalloc-opspercpusec.vs.threads.1024.bytes.png
vendored
Normal file
After Width: | Height: | Size: 1.8 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/tcmalloc-opspercpusec.vs.threads.128.bytes.png
vendored
Normal file
After Width: | Height: | Size: 1.7 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/tcmalloc-opspercpusec.vs.threads.131072.bytes.png
vendored
Normal file
After Width: | Height: | Size: 1.3 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/tcmalloc-opspercpusec.vs.threads.16384.bytes.png
vendored
Normal file
After Width: | Height: | Size: 1.8 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/tcmalloc-opspercpusec.vs.threads.2048.bytes.png
vendored
Normal file
After Width: | Height: | Size: 1.8 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/tcmalloc-opspercpusec.vs.threads.256.bytes.png
vendored
Normal file
After Width: | Height: | Size: 1.8 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/tcmalloc-opspercpusec.vs.threads.32768.bytes.png
vendored
Normal file
After Width: | Height: | Size: 1.5 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/tcmalloc-opspercpusec.vs.threads.4096.bytes.png
vendored
Normal file
After Width: | Height: | Size: 2 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/tcmalloc-opspercpusec.vs.threads.512.bytes.png
vendored
Normal file
After Width: | Height: | Size: 1.6 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/tcmalloc-opspercpusec.vs.threads.64.bytes.png
vendored
Normal file
After Width: | Height: | Size: 1.6 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/tcmalloc-opspercpusec.vs.threads.65536.bytes.png
vendored
Normal file
After Width: | Height: | Size: 1.5 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/tcmalloc-opspercpusec.vs.threads.8192.bytes.png
vendored
Normal file
After Width: | Height: | Size: 1.9 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/tcmalloc-opspersec.vs.size.1.threads.png
vendored
Normal file
After Width: | Height: | Size: 1.6 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/tcmalloc-opspersec.vs.size.12.threads.png
vendored
Normal file
After Width: | Height: | Size: 2.2 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/tcmalloc-opspersec.vs.size.16.threads.png
vendored
Normal file
After Width: | Height: | Size: 2 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/tcmalloc-opspersec.vs.size.2.threads.png
vendored
Normal file
After Width: | Height: | Size: 2.1 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/tcmalloc-opspersec.vs.size.20.threads.png
vendored
Normal file
After Width: | Height: | Size: 2.1 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/tcmalloc-opspersec.vs.size.3.threads.png
vendored
Normal file
After Width: | Height: | Size: 2.2 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/tcmalloc-opspersec.vs.size.4.threads.png
vendored
Normal file
After Width: | Height: | Size: 2.1 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/tcmalloc-opspersec.vs.size.5.threads.png
vendored
Normal file
After Width: | Height: | Size: 1.9 KiB |
BIN
trunk/3rdparty/gperftools-2-fit/docs/tcmalloc-opspersec.vs.size.8.threads.png
vendored
Normal file
After Width: | Height: | Size: 2.1 KiB |
778
trunk/3rdparty/gperftools-2-fit/docs/tcmalloc.html
vendored
Normal file
|
@ -0,0 +1,778 @@
|
|||
<!doctype html public "-//w3c//dtd html 4.01 transitional//en">
|
||||
<!-- $Id: $ -->
|
||||
<html>
|
||||
<head>
|
||||
<title>TCMalloc : Thread-Caching Malloc</title>
|
||||
<link rel="stylesheet" href="designstyle.css">
|
||||
<style type="text/css">
|
||||
em {
|
||||
color: red;
|
||||
font-style: normal;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
|
||||
<h1>TCMalloc : Thread-Caching Malloc</h1>
|
||||
|
||||
<address>Sanjay Ghemawat</address>
|
||||
|
||||
<h2><A name=motivation>Motivation</A></h2>
|
||||
|
||||
<p>TCMalloc is faster than the glibc 2.3 malloc (available as a
|
||||
separate library called ptmalloc2) and other mallocs that I have
|
||||
tested. ptmalloc2 takes approximately 300 nanoseconds to execute a
|
||||
malloc/free pair on a 2.8 GHz P4 (for small objects). The TCMalloc
|
||||
implementation takes approximately 50 nanoseconds for the same
|
||||
operation pair. Speed is important for a malloc implementation
|
||||
because if malloc is not fast enough, application writers are inclined
|
||||
to write their own custom free lists on top of malloc. This can lead
|
||||
to extra complexity, and more memory usage unless the application
|
||||
writer is very careful to appropriately size the free lists and
|
||||
scavenge idle objects out of the free list.</p>
|
||||
|
||||
<p>TCMalloc also reduces lock contention for multi-threaded programs.
|
||||
For small objects, there is virtually zero contention. For large
|
||||
objects, TCMalloc tries to use fine grained and efficient spinlocks.
|
||||
ptmalloc2 also reduces lock contention by using per-thread arenas but
|
||||
there is a big problem with ptmalloc2's use of per-thread arenas. In
|
||||
ptmalloc2 memory can never move from one arena to another. This can
|
||||
lead to huge amounts of wasted space. For example, in one Google
|
||||
application, the first phase would allocate approximately 300MB of
|
||||
memory for its URL canonicalization data structures. When the first
|
||||
phase finished, a second phase would be started in the same address
|
||||
space. If this second phase was assigned a different arena than the
|
||||
one used by the first phase, this phase would not reuse any of the
|
||||
memory left after the first phase and would add another 300MB to the
|
||||
address space. Similar memory blowup problems were also noticed in
|
||||
other applications.</p>
|
||||
|
||||
<p>Another benefit of TCMalloc is space-efficient representation of
|
||||
small objects. For example, N 8-byte objects can be allocated while
|
||||
using space approximately <code>8N * 1.01</code> bytes. I.e., a
|
||||
one-percent space overhead. ptmalloc2 uses a four-byte header for
|
||||
each object and (I think) rounds up the size to a multiple of 8 bytes
|
||||
and ends up using <code>16N</code> bytes.</p>
|
||||
|
||||
|
||||
<h2><A NAME="Usage">Usage</A></h2>
|
||||
|
||||
<p>To use TCMalloc, just link TCMalloc into your application via the
|
||||
"-ltcmalloc" linker flag.</p>
|
||||
|
||||
<p>You can use TCMalloc in applications you didn't compile yourself,
|
||||
by using LD_PRELOAD:</p>
|
||||
<pre>
|
||||
$ LD_PRELOAD="/usr/lib/libtcmalloc.so" <binary>
|
||||
</pre>
|
||||
<p>LD_PRELOAD is tricky, and we don't necessarily recommend this mode
|
||||
of usage.</p>
|
||||
|
||||
<p>TCMalloc includes a <A HREF="heap_checker.html">heap checker</A>
|
||||
and <A HREF="heapprofile.html">heap profiler</A> as well.</p>
|
||||
|
||||
<p>If you'd rather link in a version of TCMalloc that does not include
|
||||
the heap profiler and checker (perhaps to reduce binary size for a
|
||||
static binary), you can link in <code>libtcmalloc_minimal</code>
|
||||
instead.</p>
|
||||
|
||||
|
||||
<h2><A NAME="Overview">Overview</A></h2>
|
||||
|
||||
<p>TCMalloc assigns each thread a thread-local cache. Small
|
||||
allocations are satisfied from the thread-local cache. Objects are
|
||||
moved from central data structures into a thread-local cache as
|
||||
needed, and periodic garbage collections are used to migrate memory
|
||||
back from a thread-local cache into the central data structures.</p>
|
||||
<center><img src="overview.gif"></center>
|
||||
|
||||
<p>TCMalloc treats objects with size <= 256K ("small" objects)
|
||||
differently from larger objects. Large objects are allocated directly
|
||||
from the central heap using a page-level allocator (a page is a 8K
|
||||
aligned region of memory). I.e., a large object is always
|
||||
page-aligned and occupies an integral number of pages.</p>
|
||||
|
||||
<p>A run of pages can be carved up into a sequence of small objects,
|
||||
each equally sized. For example a run of one page (4K) can be carved
|
||||
up into 32 objects of size 128 bytes each.</p>
|
||||
|
||||
|
||||
<h2><A NAME="Small_Object_Allocation">Small Object Allocation</A></h2>
|
||||
|
||||
<p>Each small object size maps to one of approximately 88 allocatable
|
||||
size-classes. For example, all allocations in the range 961 to 1024
|
||||
bytes are rounded up to 1024. The size-classes are spaced so that
|
||||
small sizes are separated by 8 bytes, larger sizes by 16 bytes, even
|
||||
larger sizes by 32 bytes, and so forth. The maximal spacing is
|
||||
controlled so that not too much space is wasted when an allocation
|
||||
request falls just past the end of a size class and has to be rounded
|
||||
up to the next class.</p>
|
||||
|
||||
<p>A thread cache contains a singly linked list of free objects per
|
||||
size-class.</p>
|
||||
<center><img src="threadheap.gif"></center>
|
||||
|
||||
<p>When allocating a small object: (1) We map its size to the
|
||||
corresponding size-class. (2) Look in the corresponding free list in
|
||||
the thread cache for the current thread. (3) If the free list is not
|
||||
empty, we remove the first object from the list and return it. When
|
||||
following this fast path, TCMalloc acquires no locks at all. This
|
||||
helps speed-up allocation significantly because a lock/unlock pair
|
||||
takes approximately 100 nanoseconds on a 2.8 GHz Xeon.</p>
|
||||
|
||||
<p>If the free list is empty: (1) We fetch a bunch of objects from a
|
||||
central free list for this size-class (the central free list is shared
|
||||
by all threads). (2) Place them in the thread-local free list. (3)
|
||||
Return one of the newly fetched objects to the applications.</p>
|
||||
|
||||
<p>If the central free list is also empty: (1) We allocate a run of
|
||||
pages from the central page allocator. (2) Split the run into a set
|
||||
of objects of this size-class. (3) Place the new objects on the
|
||||
central free list. (4) As before, move some of these objects to the
|
||||
thread-local free list.</p>
|
||||
|
||||
<h3><A NAME="Sizing_Thread_Cache_Free_Lists">
|
||||
Sizing Thread Cache Free Lists</A></h3>
|
||||
|
||||
<p>It is important to size the thread cache free lists correctly. If
|
||||
the free list is too small, we'll need to go to the central free list
|
||||
too often. If the free list is too big, we'll waste memory as objects
|
||||
sit idle in the free list.</p>
|
||||
|
||||
<p>Note that the thread caches are just as important for deallocation
|
||||
as they are for allocation. Without a cache, each deallocation would
|
||||
require moving the memory to the central free list. Also, some threads
|
||||
have asymmetric alloc/free behavior (e.g. producer and consumer threads),
|
||||
so sizing the free list correctly gets trickier.</p>
|
||||
|
||||
<p>To size the free lists appropriately, we use a slow-start algorithm
|
||||
to determine the maximum length of each individual free list. As the
|
||||
free list is used more frequently, its maximum length grows. However,
|
||||
if a free list is used more for deallocation than allocation, its
|
||||
maximum length will grow only up to a point where the whole list can
|
||||
be efficiently moved to the central free list at once.</p>
|
||||
|
||||
<p>The psuedo-code below illustrates this slow-start algorithm. Note
|
||||
that <code>num_objects_to_move</code> is specific to each size class.
|
||||
By moving a list of objects with a well-known length, the central
|
||||
cache can efficiently pass these lists between thread caches. If
|
||||
a thread cache wants fewer than <code>num_objects_to_move</code>,
|
||||
the operation on the central free list has linear time complexity.
|
||||
The downside of always using <code>num_objects_to_move</code> as
|
||||
the number of objects to transfer to and from the central cache is
|
||||
that it wastes memory in threads that don't need all of those objects.
|
||||
|
||||
<pre>
|
||||
Start each freelist max_length at 1.
|
||||
|
||||
Allocation
|
||||
if freelist empty {
|
||||
fetch min(max_length, num_objects_to_move) from central list;
|
||||
if max_length < num_objects_to_move { // slow-start
|
||||
max_length++;
|
||||
} else {
|
||||
max_length += num_objects_to_move;
|
||||
}
|
||||
}
|
||||
|
||||
Deallocation
|
||||
if length > max_length {
|
||||
// Don't try to release num_objects_to_move if we don't have that many.
|
||||
release min(max_length, num_objects_to_move) objects to central list
|
||||
if max_length < num_objects_to_move {
|
||||
// Slow-start up to num_objects_to_move.
|
||||
max_length++;
|
||||
} else if max_length > num_objects_to_move {
|
||||
// If we consistently go over max_length, shrink max_length.
|
||||
overages++;
|
||||
if overages > kMaxOverages {
|
||||
max_length -= num_objects_to_move;
|
||||
overages = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
</pre>
|
||||
|
||||
See also the section on <a href="#Garbage_Collection">Garbage Collection</a>
|
||||
to see how it affects the <code>max_length</code>.
|
||||
|
||||
<h2><A NAME="Medium_Object_Allocation">Medium Object Allocation</A></h2>
|
||||
|
||||
<p>A medium object size (256K ≤ size ≤ 1MB) is rounded up to a page
|
||||
size (8K) and is handled by a central page heap. The central page heap
|
||||
includes an array of 128 free lists. The <code>k</code>th entry is a
|
||||
free list of runs that consist of <code>k + 1</code> pages:</p>
|
||||
<center><img src="pageheap.gif"></center>
|
||||
|
||||
<p>An allocation for <code>k</code> pages is satisfied by looking in
|
||||
the <code>k</code>th free list. If that free list is empty, we look
|
||||
in the next free list, and so forth. If no medium-object free list
|
||||
can satisfy the allocation, the allocation is treated as a large object.
|
||||
|
||||
|
||||
<h2><A NAME="Large_Object_Allocation">Large Object Allocation</A></h2>
|
||||
|
||||
Allocations of 1MB or more are considered large allocations. Spans
|
||||
of free memory which can satisfy these allocations are tracked in
|
||||
a red-black tree sorted by size. Allocations follow the <em>best-fit</em>
|
||||
algorithm: the tree is searched to find the smallest span of free
|
||||
space which is larger than the requested allocation. The allocation
|
||||
is carved out of that span, and the remaining space is reinserted
|
||||
either into the large object tree or possibly into one of the smaller
|
||||
free-lists as appropriate.
|
||||
|
||||
If no span of free memory is located that can fit the requested
|
||||
allocation, we fetch memory from the system (using <code>sbrk</code>,
|
||||
<code>mmap</code>, or by mapping in portions of
|
||||
<code>/dev/mem</code>).</p>
|
||||
|
||||
<p>If an allocation for <code>k</code> pages is satisfied by a run
|
||||
of pages of length > <code>k</code>, the remainder of the
|
||||
run is re-inserted back into the appropriate free list in the
|
||||
page heap.</p>
|
||||
|
||||
|
||||
<h2><A NAME="Spans">Spans</A></h2>
|
||||
|
||||
<p>The heap managed by TCMalloc consists of a set of pages. A run of
|
||||
contiguous pages is represented by a <code>Span</code> object. A span
|
||||
can either be <em>allocated</em>, or <em>free</em>. If free, the span
|
||||
is one of the entries in a page heap linked-list. If allocated, it is
|
||||
either a large object that has been handed off to the application, or
|
||||
a run of pages that have been split up into a sequence of small
|
||||
objects. If split into small objects, the size-class of the objects
|
||||
is recorded in the span.</p>
|
||||
|
||||
<p>A central array indexed by page number can be used to find the span to
|
||||
which a page belongs. For example, span <em>a</em> below occupies 2
|
||||
pages, span <em>b</em> occupies 1 page, span <em>c</em> occupies 5
|
||||
pages and span <em>d</em> occupies 3 pages.</p>
|
||||
<center><img src="spanmap.gif"></center>
|
||||
|
||||
<p>In a 32-bit address space, the central array is represented by a a
|
||||
2-level radix tree where the root contains 32 entries and each leaf
|
||||
contains 2^14 entries (a 32-bit address space has 2^19 8K pages, and
|
||||
the first level of tree divides the 2^19 pages by 2^5). This leads to
|
||||
a starting memory usage of 64KB of space (2^14*4 bytes) for the
|
||||
central array, which seems acceptable.</p>
|
||||
|
||||
<p>On 64-bit machines, we use a 3-level radix tree.</p>
|
||||
|
||||
|
||||
<h2><A NAME="Deallocation">Deallocation</A></h2>
|
||||
|
||||
<p>When an object is deallocated, we compute its page number and look
|
||||
it up in the central array to find the corresponding span object. The
|
||||
span tells us whether or not the object is small, and its size-class
|
||||
if it is small. If the object is small, we insert it into the
|
||||
appropriate free list in the current thread's thread cache. If the
|
||||
thread cache now exceeds a predetermined size (2MB by default), we run
|
||||
a garbage collector that moves unused objects from the thread cache
|
||||
into central free lists.</p>
|
||||
|
||||
<p>If the object is large, the span tells us the range of pages covered
|
||||
by the object. Suppose this range is <code>[p,q]</code>. We also
|
||||
lookup the spans for pages <code>p-1</code> and <code>q+1</code>. If
|
||||
either of these neighboring spans are free, we coalesce them with the
|
||||
<code>[p,q]</code> span. The resulting span is inserted into the
|
||||
appropriate free list in the page heap.</p>
|
||||
|
||||
|
||||
<h2>Central Free Lists for Small Objects</h2>
|
||||
|
||||
<p>As mentioned before, we keep a central free list for each
|
||||
size-class. Each central free list is organized as a two-level data
|
||||
structure: a set of spans, and a linked list of free objects per
|
||||
span.</p>
|
||||
|
||||
<p>An object is allocated from a central free list by removing the
|
||||
first entry from the linked list of some span. (If all spans have
|
||||
empty linked lists, a suitably sized span is first allocated from the
|
||||
central page heap.)</p>
|
||||
|
||||
<p>An object is returned to a central free list by adding it to the
|
||||
linked list of its containing span. If the linked list length now
|
||||
equals the total number of small objects in the span, this span is now
|
||||
completely free and is returned to the page heap.</p>
|
||||
|
||||
|
||||
<h2><A NAME="Garbage_Collection">Garbage Collection of Thread Caches</A></h2>
|
||||
|
||||
<p>Garbage collecting objects from a thread cache keeps the size of
|
||||
the cache under control and returns unused objects to the central free
|
||||
lists. Some threads need large caches to perform well while others
|
||||
can get by with little or no cache at all. When a thread cache goes
|
||||
over its <code>max_size</code>, garbage collection kicks in and then the
|
||||
thread competes with the other threads for a larger cache.</p>
|
||||
|
||||
<p>Garbage collection is run only during a deallocation. We walk over
|
||||
all free lists in the cache and move some number of objects from the
|
||||
free list to the corresponding central list.</p>
|
||||
|
||||
<p>The number of objects to be moved from a free list is determined
|
||||
using a per-list low-water-mark <code>L</code>. <code>L</code>
|
||||
records the minimum length of the list since the last garbage
|
||||
collection. Note that we could have shortened the list by
|
||||
<code>L</code> objects at the last garbage collection without
|
||||
requiring any extra accesses to the central list. We use this past
|
||||
history as a predictor of future accesses and move <code>L/2</code>
|
||||
objects from the thread cache free list to the corresponding central
|
||||
free list. This algorithm has the nice property that if a thread
|
||||
stops using a particular size, all objects of that size will quickly
|
||||
move from the thread cache to the central free list where they can be
|
||||
used by other threads.</p>
|
||||
|
||||
<p>If a thread consistently deallocates more objects of a certain size
|
||||
than it allocates, this <code>L/2</code> behavior will cause at least
|
||||
<code>L/2</code> objects to always sit in the free list. To avoid
|
||||
wasting memory this way, we shrink the maximum length of the freelist
|
||||
to converge on <code>num_objects_to_move</code> (see also
|
||||
<a href="#Sizing_Thread_Cache_Free_Lists">Sizing Thread Cache Free Lists</a>).
|
||||
|
||||
<pre>
|
||||
Garbage Collection
|
||||
if (L != 0 && max_length > num_objects_to_move) {
|
||||
max_length = max(max_length - num_objects_to_move, num_objects_to_move)
|
||||
}
|
||||
</pre>
|
||||
|
||||
<p>The fact that the thread cache went over its <code>max_size</code> is
|
||||
an indication that the thread would benefit from a larger cache. Simply
|
||||
increasing <code>max_size</code> would use an inordinate amount of memory
|
||||
in programs that have lots of active threads. Developers can bound the
|
||||
memory used with the flag --tcmalloc_max_total_thread_cache_bytes.</p>
|
||||
|
||||
<p>Each thread cache starts with a small <code>max_size</code>
|
||||
(e.g. 64KB) so that idle threads won't pre-allocate memory they don't
|
||||
need. Each time the cache runs a garbage collection, it will also try
|
||||
to grow its <code>max_size</code>. If the sum of the thread cache
|
||||
sizes is less than --tcmalloc_max_total_thread_cache_bytes,
|
||||
<code>max_size</code> grows easily. If not, thread cache 1 will try
|
||||
to steal from thread cache 2 (picked round-robin) by decreasing thread
|
||||
cache 2's <code>max_size</code>. In this way, threads that are more
|
||||
active will steal memory from other threads more often than they are
|
||||
have memory stolen from themselves. Mostly idle threads end up with
|
||||
small caches and active threads end up with big caches. Note that
|
||||
this stealing can cause the sum of the thread cache sizes to be
|
||||
greater than --tcmalloc_max_total_thread_cache_bytes until thread
|
||||
cache 2 deallocates some memory to trigger a garbage collection.</p>
|
||||
|
||||
<h2><A NAME="performance">Performance Notes</A></h2>
|
||||
|
||||
<h3>PTMalloc2 unittest</h3>
|
||||
|
||||
<p>The PTMalloc2 package (now part of glibc) contains a unittest
|
||||
program <code>t-test1.c</code>. This forks a number of threads and
|
||||
performs a series of allocations and deallocations in each thread; the
|
||||
threads do not communicate other than by synchronization in the memory
|
||||
allocator.</p>
|
||||
|
||||
<p><code>t-test1</code> (included in
|
||||
<code>tests/tcmalloc/</code>, and compiled as
|
||||
<code>ptmalloc_unittest1</code>) was run with a varying numbers of
|
||||
threads (1-20) and maximum allocation sizes (64 bytes -
|
||||
32Kbytes). These tests were run on a 2.4GHz dual Xeon system with
|
||||
hyper-threading enabled, using Linux glibc-2.3.2 from RedHat 9, with
|
||||
one million operations per thread in each test. In each case, the test
|
||||
was run once normally, and once with
|
||||
<code>LD_PRELOAD=libtcmalloc.so</code>.
|
||||
|
||||
<p>The graphs below show the performance of TCMalloc vs PTMalloc2 for
|
||||
several different metrics. Firstly, total operations (millions) per
|
||||
elapsed second vs max allocation size, for varying numbers of
|
||||
threads. The raw data used to generate these graphs (the output of the
|
||||
<code>time</code> utility) is available in
|
||||
<code>t-test1.times.txt</code>.</p>
|
||||
|
||||
<table>
|
||||
<tr>
|
||||
<td><img src="tcmalloc-opspersec.vs.size.1.threads.png"></td>
|
||||
<td><img src="tcmalloc-opspersec.vs.size.2.threads.png"></td>
|
||||
<td><img src="tcmalloc-opspersec.vs.size.3.threads.png"></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td><img src="tcmalloc-opspersec.vs.size.4.threads.png"></td>
|
||||
<td><img src="tcmalloc-opspersec.vs.size.5.threads.png"></td>
|
||||
<td><img src="tcmalloc-opspersec.vs.size.8.threads.png"></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td><img src="tcmalloc-opspersec.vs.size.12.threads.png"></td>
|
||||
<td><img src="tcmalloc-opspersec.vs.size.16.threads.png"></td>
|
||||
<td><img src="tcmalloc-opspersec.vs.size.20.threads.png"></td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
|
||||
<ul>
|
||||
<li> TCMalloc is much more consistently scalable than PTMalloc2 - for
|
||||
all thread counts >1 it achieves ~7-9 million ops/sec for small
|
||||
allocations, falling to ~2 million ops/sec for larger
|
||||
allocations. The single-thread case is an obvious outlier,
|
||||
since it is only able to keep a single processor busy and hence
|
||||
can achieve fewer ops/sec. PTMalloc2 has a much higher variance
|
||||
on operations/sec - peaking somewhere around 4 million ops/sec
|
||||
for small allocations and falling to <1 million ops/sec for
|
||||
larger allocations.
|
||||
|
||||
<li> TCMalloc is faster than PTMalloc2 in the vast majority of
|
||||
cases, and particularly for small allocations. Contention
|
||||
between threads is less of a problem in TCMalloc.
|
||||
|
||||
<li> TCMalloc's performance drops off as the allocation size
|
||||
increases. This is because the per-thread cache is
|
||||
garbage-collected when it hits a threshold (defaulting to
|
||||
2MB). With larger allocation sizes, fewer objects can be stored
|
||||
in the cache before it is garbage-collected.
|
||||
|
||||
<li> There is a noticeable drop in TCMalloc's performance at ~32K
|
||||
maximum allocation size; at larger sizes performance drops less
|
||||
quickly. This is due to the 32K maximum size of objects in the
|
||||
per-thread caches; for objects larger than this TCMalloc
|
||||
allocates from the central page heap.
|
||||
</ul>
|
||||
|
||||
<p>Next, operations (millions) per second of CPU time vs number of
|
||||
threads, for max allocation size 64 bytes - 128 Kbytes.</p>
|
||||
|
||||
<table>
|
||||
<tr>
|
||||
<td><img src="tcmalloc-opspercpusec.vs.threads.64.bytes.png"></td>
|
||||
<td><img src="tcmalloc-opspercpusec.vs.threads.256.bytes.png"></td>
|
||||
<td><img src="tcmalloc-opspercpusec.vs.threads.1024.bytes.png"></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td><img src="tcmalloc-opspercpusec.vs.threads.4096.bytes.png"></td>
|
||||
<td><img src="tcmalloc-opspercpusec.vs.threads.8192.bytes.png"></td>
|
||||
<td><img src="tcmalloc-opspercpusec.vs.threads.16384.bytes.png"></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td><img src="tcmalloc-opspercpusec.vs.threads.32768.bytes.png"></td>
|
||||
<td><img src="tcmalloc-opspercpusec.vs.threads.65536.bytes.png"></td>
|
||||
<td><img src="tcmalloc-opspercpusec.vs.threads.131072.bytes.png"></td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
<p>Here we see again that TCMalloc is both more consistent and more
|
||||
efficient than PTMalloc2. For max allocation sizes <32K, TCMalloc
|
||||
typically achieves ~2-2.5 million ops per second of CPU time with a
|
||||
large number of threads, whereas PTMalloc achieves generally 0.5-1
|
||||
million ops per second of CPU time, with a lot of cases achieving much
|
||||
less than this figure. Above 32K max allocation size, TCMalloc drops
|
||||
to 1-1.5 million ops per second of CPU time, and PTMalloc drops almost
|
||||
to zero for large numbers of threads (i.e. with PTMalloc, lots of CPU
|
||||
time is being burned spinning waiting for locks in the heavily
|
||||
multi-threaded case).</p>
|
||||
|
||||
|
||||
<H2><A NAME="runtime">Modifying Runtime Behavior</A></H2>
|
||||
|
||||
<p>You can more finely control the behavior of the tcmalloc via
|
||||
environment variables.</p>
|
||||
|
||||
<p>Generally useful flags:</p>
|
||||
|
||||
<table frame=box rules=sides cellpadding=5 width=100%>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>TCMALLOC_SAMPLE_PARAMETER</code></td>
|
||||
<td>default: 0</td>
|
||||
<td>
|
||||
The approximate gap between sampling actions. That is, we
|
||||
take one sample approximately once every
|
||||
<code>tcmalloc_sample_parmeter</code> bytes of allocation.
|
||||
This sampled heap information is available via
|
||||
<code>MallocExtension::GetHeapSample()</code> or
|
||||
<code>MallocExtension::ReadStackTraces()</code>. A reasonable
|
||||
value is 524288.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>TCMALLOC_RELEASE_RATE</code></td>
|
||||
<td>default: 1.0</td>
|
||||
<td>
|
||||
Rate at which we release unused memory to the system, via
|
||||
<code>madvise(MADV_DONTNEED)</code>, on systems that support
|
||||
it. Zero means we never release memory back to the system.
|
||||
Increase this flag to return memory faster; decrease it
|
||||
to return memory slower. Reasonable rates are in the
|
||||
range [0,10].
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>TCMALLOC_LARGE_ALLOC_REPORT_THRESHOLD</code></td>
|
||||
<td>default: 1073741824</td>
|
||||
<td>
|
||||
Allocations larger than this value cause a stack trace to be
|
||||
dumped to stderr. The threshold for dumping stack traces is
|
||||
increased by a factor of 1.125 every time we print a message so
|
||||
that the threshold automatically goes up by a factor of ~1000
|
||||
every 60 messages. This bounds the amount of extra logging
|
||||
generated by this flag. Default value of this flag is very large
|
||||
and therefore you should see no extra logging unless the flag is
|
||||
overridden.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>TCMALLOC_MAX_TOTAL_THREAD_CACHE_BYTES</code></td>
|
||||
<td>default: 16777216</td>
|
||||
<td>
|
||||
Bound on the total amount of bytes allocated to thread caches. This
|
||||
bound is not strict, so it is possible for the cache to go over this
|
||||
bound in certain circumstances. This value defaults to 16MB. For
|
||||
applications with many threads, this may not be a large enough cache,
|
||||
which can affect performance. If you suspect your application is not
|
||||
scaling to many threads due to lock contention in TCMalloc, you can
|
||||
try increasing this value. This may improve performance, at a cost
|
||||
of extra memory use by TCMalloc. See <a href="#Garbage_Collection">
|
||||
Garbage Collection</a> for more details.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
</table>
|
||||
|
||||
<p>Advanced "tweaking" flags, that control more precisely how tcmalloc
|
||||
tries to allocate memory from the kernel.</p>
|
||||
|
||||
<table frame=box rules=sides cellpadding=5 width=100%>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>TCMALLOC_SKIP_MMAP</code></td>
|
||||
<td>default: false</td>
|
||||
<td>
|
||||
If true, do not try to use <code>mmap</code> to obtain memory
|
||||
from the kernel.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>TCMALLOC_SKIP_SBRK</code></td>
|
||||
<td>default: false</td>
|
||||
<td>
|
||||
If true, do not try to use <code>sbrk</code> to obtain memory
|
||||
from the kernel.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>TCMALLOC_DEVMEM_START</code></td>
|
||||
<td>default: 0</td>
|
||||
<td>
|
||||
Physical memory starting location in MB for <code>/dev/mem</code>
|
||||
allocation. Setting this to 0 disables <code>/dev/mem</code>
|
||||
allocation.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>TCMALLOC_DEVMEM_LIMIT</code></td>
|
||||
<td>default: 0</td>
|
||||
<td>
|
||||
Physical memory limit location in MB for <code>/dev/mem</code>
|
||||
allocation. Setting this to 0 means no limit.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>TCMALLOC_DEVMEM_DEVICE</code></td>
|
||||
<td>default: /dev/mem</td>
|
||||
<td>
|
||||
Device to use for allocating unmanaged memory.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>TCMALLOC_MEMFS_MALLOC_PATH</code></td>
|
||||
<td>default: ""</td>
|
||||
<td>
|
||||
If set, specify a path where hugetlbfs or tmpfs is mounted.
|
||||
This may allow for speedier allocations.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>TCMALLOC_MEMFS_LIMIT_MB</code></td>
|
||||
<td>default: 0</td>
|
||||
<td>
|
||||
Limit total memfs allocation size to specified number of MB.
|
||||
0 means "no limit".
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>TCMALLOC_MEMFS_ABORT_ON_FAIL</code></td>
|
||||
<td>default: false</td>
|
||||
<td>
|
||||
If true, abort() whenever memfs_malloc fails to satisfy an allocation.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>TCMALLOC_MEMFS_IGNORE_MMAP_FAIL</code></td>
|
||||
<td>default: false</td>
|
||||
<td>
|
||||
If true, ignore failures from mmap.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>TCMALLOC_MEMFS_MAP_PRIVATE</code></td>
|
||||
<td>default: false</td>
|
||||
<td>
|
||||
If true, use MAP_PRIVATE when mapping via memfs, not MAP_SHARED.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
</table>
|
||||
|
||||
|
||||
<H2><A NAME="compiletime">Modifying Behavior In Code</A></H2>
|
||||
|
||||
<p>The <code>MallocExtension</code> class, in
|
||||
<code>malloc_extension.h</code>, provides a few knobs that you can
|
||||
tweak in your program, to affect tcmalloc's behavior.</p>
|
||||
|
||||
<h3>Releasing Memory Back to the System</h3>
|
||||
|
||||
<p>By default, tcmalloc will release no-longer-used memory back to the
|
||||
kernel gradually, over time. The <a
|
||||
href="#runtime">tcmalloc_release_rate</a> flag controls how quickly
|
||||
this happens. You can also force a release at a given point in the
|
||||
progam execution like so:</p>
|
||||
<pre>
|
||||
MallocExtension::instance()->ReleaseFreeMemory();
|
||||
</pre>
|
||||
|
||||
<p>You can also call <code>SetMemoryReleaseRate()</code> to change the
|
||||
<code>tcmalloc_release_rate</code> value at runtime, or
|
||||
<code>GetMemoryReleaseRate</code> to see what the current release rate
|
||||
is.</p>
|
||||
|
||||
<h3>Memory Introspection</h3>
|
||||
|
||||
<p>There are several routines for getting a human-readable form of the
|
||||
current memory usage:</p>
|
||||
<pre>
|
||||
MallocExtension::instance()->GetStats(buffer, buffer_length);
|
||||
MallocExtension::instance()->GetHeapSample(&string);
|
||||
MallocExtension::instance()->GetHeapGrowthStacks(&string);
|
||||
</pre>
|
||||
|
||||
<p>The last two create files in the same format as the heap-profiler,
|
||||
and can be passed as data files to pprof. The first is human-readable
|
||||
and is meant for debugging.</p>
|
||||
|
||||
<h3>Generic Tcmalloc Status</h3>
|
||||
|
||||
<p>TCMalloc has support for setting and retrieving arbitrary
|
||||
'properties':</p>
|
||||
<pre>
|
||||
MallocExtension::instance()->SetNumericProperty(property_name, value);
|
||||
MallocExtension::instance()->GetNumericProperty(property_name, &value);
|
||||
</pre>
|
||||
|
||||
<p>It is possible for an application to set and get these properties,
|
||||
but the most useful is when a library sets the properties so the
|
||||
application can read them. Here are the properties TCMalloc defines;
|
||||
you can access them with a call like
|
||||
<code>MallocExtension::instance()->GetNumericProperty("generic.heap_size",
|
||||
&value);</code>:</p>
|
||||
|
||||
<table frame=box rules=sides cellpadding=5 width=100%>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>generic.current_allocated_bytes</code></td>
|
||||
<td>
|
||||
Number of bytes used by the application. This will not typically
|
||||
match the memory use reported by the OS, because it does not
|
||||
include TCMalloc overhead or memory fragmentation.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>generic.heap_size</code></td>
|
||||
<td>
|
||||
Bytes of system memory reserved by TCMalloc.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>tcmalloc.pageheap_free_bytes</code></td>
|
||||
<td>
|
||||
Number of bytes in free, mapped pages in page heap. These bytes
|
||||
can be used to fulfill allocation requests. They always count
|
||||
towards virtual memory usage, and unless the underlying memory is
|
||||
swapped out by the OS, they also count towards physical memory
|
||||
usage.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>tcmalloc.pageheap_unmapped_bytes</code></td>
|
||||
<td>
|
||||
Number of bytes in free, unmapped pages in page heap. These are
|
||||
bytes that have been released back to the OS, possibly by one of
|
||||
the MallocExtension "Release" calls. They can be used to fulfill
|
||||
allocation requests, but typically incur a page fault. They
|
||||
always count towards virtual memory usage, and depending on the
|
||||
OS, typically do not count towards physical memory usage.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>tcmalloc.slack_bytes</code></td>
|
||||
<td>
|
||||
Sum of pageheap_free_bytes and pageheap_unmapped_bytes. Provided
|
||||
for backwards compatibility only. Do not use.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>tcmalloc.max_total_thread_cache_bytes</code></td>
|
||||
<td>
|
||||
A limit to how much memory TCMalloc dedicates for small objects.
|
||||
Higher numbers trade off more memory use for -- in some situations
|
||||
-- improved efficiency.
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr valign=top>
|
||||
<td><code>tcmalloc.current_total_thread_cache_bytes</code></td>
|
||||
<td>
|
||||
A measure of some of the memory TCMalloc is using (for
|
||||
small objects).
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
</table>
|
||||
|
||||
<h2><A NAME="caveats">Caveats</A></h2>
|
||||
|
||||
<p>For some systems, TCMalloc may not work correctly with
|
||||
applications that aren't linked against <code>libpthread.so</code> (or
|
||||
the equivalent on your OS). It should work on Linux using glibc 2.3,
|
||||
but other OS/libc combinations have not been tested.</p>
|
||||
|
||||
<p>TCMalloc may be somewhat more memory hungry than other mallocs,
|
||||
(but tends not to have the huge blowups that can happen with other
|
||||
mallocs). In particular, at startup TCMalloc allocates approximately
|
||||
240KB of internal memory.</p>
|
||||
|
||||
<p>Don't try to load TCMalloc into a running binary (e.g., using JNI
|
||||
in Java programs). The binary will have allocated some objects using
|
||||
the system malloc, and may try to pass them to TCMalloc for
|
||||
deallocation. TCMalloc will not be able to handle such objects.</p>
|
||||
|
||||
<hr>
|
||||
|
||||
<address>Sanjay Ghemawat, Paul Menage<br>
|
||||
<!-- Created: Tue Dec 19 10:43:14 PST 2000 -->
|
||||
<!-- hhmts start -->
|
||||
Last modified: Sat Feb 24 13:11:38 PST 2007 (csilvers)
|
||||
<!-- hhmts end -->
|
||||
</address>
|
||||
|
||||
</body>
|
||||
</html>
|
21
trunk/3rdparty/gperftools-2-fit/docs/threadheap.dot
vendored
Normal file
|
@ -0,0 +1,21 @@
|
|||
digraph ThreadHeap {
|
||||
rankdir=LR
|
||||
node [shape=box, width=0.3, height=0.3]
|
||||
nodesep=.05
|
||||
|
||||
heap [shape=record, height=2, label="<f0>class 0|<f1>class 1|<f2>class 2|..."]
|
||||
O0 [label=""]
|
||||
O1 [label=""]
|
||||
O2 [label=""]
|
||||
O3 [label=""]
|
||||
O4 [label=""]
|
||||
O5 [label=""]
|
||||
sep1 [shape=plaintext, label="..."]
|
||||
sep2 [shape=plaintext, label="..."]
|
||||
sep3 [shape=plaintext, label="..."]
|
||||
|
||||
heap:f0 -> O0 -> O1 -> sep1
|
||||
heap:f1 -> O2 -> O3 -> sep2
|
||||
heap:f2 -> O4 -> O5 -> sep3
|
||||
|
||||
}
|
BIN
trunk/3rdparty/gperftools-2-fit/docs/threadheap.gif
vendored
Normal file
After Width: | Height: | Size: 7.4 KiB |
307
trunk/3rdparty/gperftools-2-fit/gperftools.sln
vendored
Normal file
|
@ -0,0 +1,307 @@
|
|||
Microsoft Visual Studio Solution File, Format Version 12.00
|
||||
# Visual Studio 14
|
||||
VisualStudioVersion = 14.0.25420.1
|
||||
MinimumVisualStudioVersion = 10.0.40219.1
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "libtcmalloc_minimal", "vsprojects\libtcmalloc_minimal\libtcmalloc_minimal.vcxproj", "{55E2B3AE-3CA1-4DB6-97F7-0A044D6F446F}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tcmalloc_minimal_unittest", "vsprojects\tcmalloc_minimal_unittest\tcmalloc_minimal_unittest.vcxproj", "{7CC73D97-C057-43A6-82EF-E6B567488D02}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tcmalloc_minimal_large_unittest", "vsprojects\tcmalloc_minimal_large\tcmalloc_minimal_large_unittest.vcxproj", "{2D8B9599-C74C-4298-B723-6CF6077563E3}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "addressmap_unittest", "vsprojects\addressmap_unittest\addressmap_unittest.vcxproj", "{32EECEB6-7D18-477E-BC7A-30CE98457A88}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "frag_unittest", "vsprojects\frag_unittest\frag_unittest.vcxproj", "{24754725-DE0D-4214-8979-324247AAD78E}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "low_level_alloc_unittest", "vsprojects\low_level_alloc_unittest\low_level_alloc_unittest.vcxproj", "{A765198D-5305-4AB0-9A21-A0CD8201EB2A}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "malloc_hook_test", "vsprojects\malloc_hook_test\malloc_hook_test.vcxproj", "{3765198D-AA05-4AB0-9A21-A0CD8201EB2A}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "malloc_extension_test", "vsprojects\malloc_extension_test\malloc_extension_test.vcxproj", "{3765198D-5305-4AB0-9A21-A0CD8201EB2A}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "markidle_unittest", "vsprojects\markidle_unittest\markidle_unittest.vcxproj", "{4AF7E21D-9D0A-410C-A7DB-7D21DA5166C0}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "current_allocated_bytes_test", "vsprojects\current_allocated_bytes_test\current_allocated_bytes_test.vcxproj", "{4AFFF21D-9D0A-410C-A7DB-7D21DA5166C0}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "packed-cache_test", "vsprojects\packed-cache_test\packed-cache_test.vcxproj", "{605D3CED-B530-424E-B7D2-2A31F14FD570}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "pagemap_unittest", "vsprojects\pagemap_unittest\pagemap_unittest.vcxproj", "{9765198D-5305-4AB0-9A21-A0CD8201EB2A}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "page_heap_test", "vsprojects\page_heap_test\page_heap_test.vcxproj", "{9765198D-5305-4AB0-9A21-A0CD8201EB2B}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "realloc_unittest", "vsprojects\realloc_unittest\realloc_unittest.vcxproj", "{4765198D-5305-4AB0-9A21-A0CD8201EB2A}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "sampler_test", "vsprojects\sampler_test\sampler_test.vcxproj", "{B765198D-5305-4AB0-9A21-A0CD8201EB2A}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "stack_trace_table_test", "vsprojects\stack_trace_table_test\stack_trace_table_test.vcxproj", "{A4754725-DE0D-4214-8979-324247AAD78E}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "thread_dealloc_unittest", "vsprojects\thread_dealloc_unittest\thread_dealloc_unittest.vcxproj", "{6CFFBD0F-09E3-4282-A711-0564451FDF74}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "preamble_patcher_test", "vsprojects\preamble_patcher_test\preamble_patcher_test.vcxproj", "{5765198D-5305-4AB0-9A21-A0CD8201EB2A}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "addr2line-pdb", "vsprojects\addr2line-pdb\addr2line-pdb.vcxproj", "{81CA712E-90B8-4AE5-9E89-5B436578D6DA}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "nm-pdb", "vsprojects\nm-pdb\nm-pdb.vcxproj", "{3A559C75-FD26-4300-B86B-165FD43EE1CE}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "system-alloc_unittest", "vsprojects\system-alloc_unittest\system-alloc_unittest.vcxproj", "{387F753A-0312-4A7B-A1D6-B2795E832E96}"
|
||||
EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
Debug|x64 = Debug|x64
|
||||
Debug|x86 = Debug|x86
|
||||
Release-Override|x64 = Release-Override|x64
|
||||
Release-Override|x86 = Release-Override|x86
|
||||
Release-Patch|x64 = Release-Patch|x64
|
||||
Release-Patch|x86 = Release-Patch|x86
|
||||
EndGlobalSection
|
||||
GlobalSection(ProjectConfigurationPlatforms) = postSolution
|
||||
{55E2B3AE-3CA1-4DB6-97F7-0A044D6F446F}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{55E2B3AE-3CA1-4DB6-97F7-0A044D6F446F}.Debug|x64.Build.0 = Debug|x64
|
||||
{55E2B3AE-3CA1-4DB6-97F7-0A044D6F446F}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{55E2B3AE-3CA1-4DB6-97F7-0A044D6F446F}.Debug|x86.Build.0 = Debug|Win32
|
||||
{55E2B3AE-3CA1-4DB6-97F7-0A044D6F446F}.Release-Override|x64.ActiveCfg = Release-Override|x64
|
||||
{55E2B3AE-3CA1-4DB6-97F7-0A044D6F446F}.Release-Override|x64.Build.0 = Release-Override|x64
|
||||
{55E2B3AE-3CA1-4DB6-97F7-0A044D6F446F}.Release-Override|x86.ActiveCfg = Release-Override|Win32
|
||||
{55E2B3AE-3CA1-4DB6-97F7-0A044D6F446F}.Release-Override|x86.Build.0 = Release-Override|Win32
|
||||
{55E2B3AE-3CA1-4DB6-97F7-0A044D6F446F}.Release-Patch|x64.ActiveCfg = Release-Patch|x64
|
||||
{55E2B3AE-3CA1-4DB6-97F7-0A044D6F446F}.Release-Patch|x64.Build.0 = Release-Patch|x64
|
||||
{55E2B3AE-3CA1-4DB6-97F7-0A044D6F446F}.Release-Patch|x86.ActiveCfg = Release-Patch|Win32
|
||||
{55E2B3AE-3CA1-4DB6-97F7-0A044D6F446F}.Release-Patch|x86.Build.0 = Release-Patch|Win32
|
||||
{7CC73D97-C057-43A6-82EF-E6B567488D02}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{7CC73D97-C057-43A6-82EF-E6B567488D02}.Debug|x64.Build.0 = Debug|x64
|
||||
{7CC73D97-C057-43A6-82EF-E6B567488D02}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{7CC73D97-C057-43A6-82EF-E6B567488D02}.Debug|x86.Build.0 = Debug|Win32
|
||||
{7CC73D97-C057-43A6-82EF-E6B567488D02}.Release-Override|x64.ActiveCfg = Release-Override|x64
|
||||
{7CC73D97-C057-43A6-82EF-E6B567488D02}.Release-Override|x64.Build.0 = Release-Override|x64
|
||||
{7CC73D97-C057-43A6-82EF-E6B567488D02}.Release-Override|x86.ActiveCfg = Release-Override|Win32
|
||||
{7CC73D97-C057-43A6-82EF-E6B567488D02}.Release-Override|x86.Build.0 = Release-Override|Win32
|
||||
{7CC73D97-C057-43A6-82EF-E6B567488D02}.Release-Patch|x64.ActiveCfg = Release-Patch|x64
|
||||
{7CC73D97-C057-43A6-82EF-E6B567488D02}.Release-Patch|x64.Build.0 = Release-Patch|x64
|
||||
{7CC73D97-C057-43A6-82EF-E6B567488D02}.Release-Patch|x86.ActiveCfg = Release-Patch|Win32
|
||||
{7CC73D97-C057-43A6-82EF-E6B567488D02}.Release-Patch|x86.Build.0 = Release-Patch|Win32
|
||||
{2D8B9599-C74C-4298-B723-6CF6077563E3}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{2D8B9599-C74C-4298-B723-6CF6077563E3}.Debug|x64.Build.0 = Debug|x64
|
||||
{2D8B9599-C74C-4298-B723-6CF6077563E3}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{2D8B9599-C74C-4298-B723-6CF6077563E3}.Debug|x86.Build.0 = Debug|Win32
|
||||
{2D8B9599-C74C-4298-B723-6CF6077563E3}.Release-Override|x64.ActiveCfg = Release-Override|x64
|
||||
{2D8B9599-C74C-4298-B723-6CF6077563E3}.Release-Override|x64.Build.0 = Release-Override|x64
|
||||
{2D8B9599-C74C-4298-B723-6CF6077563E3}.Release-Override|x86.ActiveCfg = Release-Override|Win32
|
||||
{2D8B9599-C74C-4298-B723-6CF6077563E3}.Release-Override|x86.Build.0 = Release-Override|Win32
|
||||
{2D8B9599-C74C-4298-B723-6CF6077563E3}.Release-Patch|x64.ActiveCfg = Release-Patch|x64
|
||||
{2D8B9599-C74C-4298-B723-6CF6077563E3}.Release-Patch|x64.Build.0 = Release-Patch|x64
|
||||
{2D8B9599-C74C-4298-B723-6CF6077563E3}.Release-Patch|x86.ActiveCfg = Release-Patch|Win32
|
||||
{2D8B9599-C74C-4298-B723-6CF6077563E3}.Release-Patch|x86.Build.0 = Release-Patch|Win32
|
||||
{32EECEB6-7D18-477E-BC7A-30CE98457A88}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{32EECEB6-7D18-477E-BC7A-30CE98457A88}.Debug|x64.Build.0 = Debug|x64
|
||||
{32EECEB6-7D18-477E-BC7A-30CE98457A88}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{32EECEB6-7D18-477E-BC7A-30CE98457A88}.Debug|x86.Build.0 = Debug|Win32
|
||||
{32EECEB6-7D18-477E-BC7A-30CE98457A88}.Release-Override|x64.ActiveCfg = Release-Override|x64
|
||||
{32EECEB6-7D18-477E-BC7A-30CE98457A88}.Release-Override|x64.Build.0 = Release-Override|x64
|
||||
{32EECEB6-7D18-477E-BC7A-30CE98457A88}.Release-Override|x86.ActiveCfg = Release-Override|Win32
|
||||
{32EECEB6-7D18-477E-BC7A-30CE98457A88}.Release-Override|x86.Build.0 = Release-Override|Win32
|
||||
{32EECEB6-7D18-477E-BC7A-30CE98457A88}.Release-Patch|x64.ActiveCfg = Release-Patch|x64
|
||||
{32EECEB6-7D18-477E-BC7A-30CE98457A88}.Release-Patch|x64.Build.0 = Release-Patch|x64
|
||||
{32EECEB6-7D18-477E-BC7A-30CE98457A88}.Release-Patch|x86.ActiveCfg = Release-Patch|Win32
|
||||
{32EECEB6-7D18-477E-BC7A-30CE98457A88}.Release-Patch|x86.Build.0 = Release-Patch|Win32
|
||||
{24754725-DE0D-4214-8979-324247AAD78E}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{24754725-DE0D-4214-8979-324247AAD78E}.Debug|x64.Build.0 = Debug|x64
|
||||
{24754725-DE0D-4214-8979-324247AAD78E}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{24754725-DE0D-4214-8979-324247AAD78E}.Debug|x86.Build.0 = Debug|Win32
|
||||
{24754725-DE0D-4214-8979-324247AAD78E}.Release-Override|x64.ActiveCfg = Release-Override|x64
|
||||
{24754725-DE0D-4214-8979-324247AAD78E}.Release-Override|x64.Build.0 = Release-Override|x64
|
||||
{24754725-DE0D-4214-8979-324247AAD78E}.Release-Override|x86.ActiveCfg = Release-Override|Win32
|
||||
{24754725-DE0D-4214-8979-324247AAD78E}.Release-Override|x86.Build.0 = Release-Override|Win32
|
||||
{24754725-DE0D-4214-8979-324247AAD78E}.Release-Patch|x64.ActiveCfg = Release-Patch|x64
|
||||
{24754725-DE0D-4214-8979-324247AAD78E}.Release-Patch|x64.Build.0 = Release-Patch|x64
|
||||
{24754725-DE0D-4214-8979-324247AAD78E}.Release-Patch|x86.ActiveCfg = Release-Patch|Win32
|
||||
{24754725-DE0D-4214-8979-324247AAD78E}.Release-Patch|x86.Build.0 = Release-Patch|Win32
|
||||
{A765198D-5305-4AB0-9A21-A0CD8201EB2A}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{A765198D-5305-4AB0-9A21-A0CD8201EB2A}.Debug|x64.Build.0 = Debug|x64
|
||||
{A765198D-5305-4AB0-9A21-A0CD8201EB2A}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{A765198D-5305-4AB0-9A21-A0CD8201EB2A}.Debug|x86.Build.0 = Debug|Win32
|
||||
{A765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Override|x64.ActiveCfg = Release-Override|x64
|
||||
{A765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Override|x64.Build.0 = Release-Override|x64
|
||||
{A765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Override|x86.ActiveCfg = Release-Override|Win32
|
||||
{A765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Override|x86.Build.0 = Release-Override|Win32
|
||||
{A765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x64.ActiveCfg = Release-Patch|x64
|
||||
{A765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x64.Build.0 = Release-Patch|x64
|
||||
{A765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x86.ActiveCfg = Release-Patch|Win32
|
||||
{A765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x86.Build.0 = Release-Patch|Win32
|
||||
{3765198D-AA05-4AB0-9A21-A0CD8201EB2A}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{3765198D-AA05-4AB0-9A21-A0CD8201EB2A}.Debug|x64.Build.0 = Debug|x64
|
||||
{3765198D-AA05-4AB0-9A21-A0CD8201EB2A}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{3765198D-AA05-4AB0-9A21-A0CD8201EB2A}.Debug|x86.Build.0 = Debug|Win32
|
||||
{3765198D-AA05-4AB0-9A21-A0CD8201EB2A}.Release-Override|x64.ActiveCfg = Release-Override|x64
|
||||
{3765198D-AA05-4AB0-9A21-A0CD8201EB2A}.Release-Override|x64.Build.0 = Release-Override|x64
|
||||
{3765198D-AA05-4AB0-9A21-A0CD8201EB2A}.Release-Override|x86.ActiveCfg = Release-Override|Win32
|
||||
{3765198D-AA05-4AB0-9A21-A0CD8201EB2A}.Release-Override|x86.Build.0 = Release-Override|Win32
|
||||
{3765198D-AA05-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x64.ActiveCfg = Release-Patch|x64
|
||||
{3765198D-AA05-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x64.Build.0 = Release-Patch|x64
|
||||
{3765198D-AA05-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x86.ActiveCfg = Release-Patch|Win32
|
||||
{3765198D-AA05-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x86.Build.0 = Release-Patch|Win32
|
||||
{3765198D-5305-4AB0-9A21-A0CD8201EB2A}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{3765198D-5305-4AB0-9A21-A0CD8201EB2A}.Debug|x64.Build.0 = Debug|x64
|
||||
{3765198D-5305-4AB0-9A21-A0CD8201EB2A}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{3765198D-5305-4AB0-9A21-A0CD8201EB2A}.Debug|x86.Build.0 = Debug|Win32
|
||||
{3765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Override|x64.ActiveCfg = Release-Override|x64
|
||||
{3765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Override|x64.Build.0 = Release-Override|x64
|
||||
{3765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Override|x86.ActiveCfg = Release-Override|Win32
|
||||
{3765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Override|x86.Build.0 = Release-Override|Win32
|
||||
{3765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x64.ActiveCfg = Release-Patch|x64
|
||||
{3765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x64.Build.0 = Release-Patch|x64
|
||||
{3765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x86.ActiveCfg = Release-Patch|Win32
|
||||
{3765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x86.Build.0 = Release-Patch|Win32
|
||||
{4AF7E21D-9D0A-410C-A7DB-7D21DA5166C0}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{4AF7E21D-9D0A-410C-A7DB-7D21DA5166C0}.Debug|x64.Build.0 = Debug|x64
|
||||
{4AF7E21D-9D0A-410C-A7DB-7D21DA5166C0}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{4AF7E21D-9D0A-410C-A7DB-7D21DA5166C0}.Debug|x86.Build.0 = Debug|Win32
|
||||
{4AF7E21D-9D0A-410C-A7DB-7D21DA5166C0}.Release-Override|x64.ActiveCfg = Release-Override|x64
|
||||
{4AF7E21D-9D0A-410C-A7DB-7D21DA5166C0}.Release-Override|x64.Build.0 = Release-Override|x64
|
||||
{4AF7E21D-9D0A-410C-A7DB-7D21DA5166C0}.Release-Override|x86.ActiveCfg = Release-Override|Win32
|
||||
{4AF7E21D-9D0A-410C-A7DB-7D21DA5166C0}.Release-Override|x86.Build.0 = Release-Override|Win32
|
||||
{4AF7E21D-9D0A-410C-A7DB-7D21DA5166C0}.Release-Patch|x64.ActiveCfg = Release-Patch|x64
|
||||
{4AF7E21D-9D0A-410C-A7DB-7D21DA5166C0}.Release-Patch|x64.Build.0 = Release-Patch|x64
|
||||
{4AF7E21D-9D0A-410C-A7DB-7D21DA5166C0}.Release-Patch|x86.ActiveCfg = Release-Patch|Win32
|
||||
{4AF7E21D-9D0A-410C-A7DB-7D21DA5166C0}.Release-Patch|x86.Build.0 = Release-Patch|Win32
|
||||
{4AFFF21D-9D0A-410C-A7DB-7D21DA5166C0}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{4AFFF21D-9D0A-410C-A7DB-7D21DA5166C0}.Debug|x64.Build.0 = Debug|x64
|
||||
{4AFFF21D-9D0A-410C-A7DB-7D21DA5166C0}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{4AFFF21D-9D0A-410C-A7DB-7D21DA5166C0}.Debug|x86.Build.0 = Debug|Win32
|
||||
{4AFFF21D-9D0A-410C-A7DB-7D21DA5166C0}.Release-Override|x64.ActiveCfg = Release-Override|x64
|
||||
{4AFFF21D-9D0A-410C-A7DB-7D21DA5166C0}.Release-Override|x64.Build.0 = Release-Override|x64
|
||||
{4AFFF21D-9D0A-410C-A7DB-7D21DA5166C0}.Release-Override|x86.ActiveCfg = Release-Override|Win32
|
||||
{4AFFF21D-9D0A-410C-A7DB-7D21DA5166C0}.Release-Override|x86.Build.0 = Release-Override|Win32
|
||||
{4AFFF21D-9D0A-410C-A7DB-7D21DA5166C0}.Release-Patch|x64.ActiveCfg = Release-Patch|x64
|
||||
{4AFFF21D-9D0A-410C-A7DB-7D21DA5166C0}.Release-Patch|x64.Build.0 = Release-Patch|x64
|
||||
{4AFFF21D-9D0A-410C-A7DB-7D21DA5166C0}.Release-Patch|x86.ActiveCfg = Release-Patch|Win32
|
||||
{4AFFF21D-9D0A-410C-A7DB-7D21DA5166C0}.Release-Patch|x86.Build.0 = Release-Patch|Win32
|
||||
{605D3CED-B530-424E-B7D2-2A31F14FD570}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{605D3CED-B530-424E-B7D2-2A31F14FD570}.Debug|x64.Build.0 = Debug|x64
|
||||
{605D3CED-B530-424E-B7D2-2A31F14FD570}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{605D3CED-B530-424E-B7D2-2A31F14FD570}.Debug|x86.Build.0 = Debug|Win32
|
||||
{605D3CED-B530-424E-B7D2-2A31F14FD570}.Release-Override|x64.ActiveCfg = Release-Override|x64
|
||||
{605D3CED-B530-424E-B7D2-2A31F14FD570}.Release-Override|x64.Build.0 = Release-Override|x64
|
||||
{605D3CED-B530-424E-B7D2-2A31F14FD570}.Release-Override|x86.ActiveCfg = Release-Override|Win32
|
||||
{605D3CED-B530-424E-B7D2-2A31F14FD570}.Release-Override|x86.Build.0 = Release-Override|Win32
|
||||
{605D3CED-B530-424E-B7D2-2A31F14FD570}.Release-Patch|x64.ActiveCfg = Release-Patch|x64
|
||||
{605D3CED-B530-424E-B7D2-2A31F14FD570}.Release-Patch|x64.Build.0 = Release-Patch|x64
|
||||
{605D3CED-B530-424E-B7D2-2A31F14FD570}.Release-Patch|x86.ActiveCfg = Release-Patch|Win32
|
||||
{605D3CED-B530-424E-B7D2-2A31F14FD570}.Release-Patch|x86.Build.0 = Release-Patch|Win32
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2A}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2A}.Debug|x64.Build.0 = Debug|x64
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2A}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2A}.Debug|x86.Build.0 = Debug|Win32
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Override|x64.ActiveCfg = Release-Override|x64
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Override|x64.Build.0 = Release-Override|x64
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Override|x86.ActiveCfg = Release-Override|Win32
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Override|x86.Build.0 = Release-Override|Win32
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x64.ActiveCfg = Release-Patch|x64
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x64.Build.0 = Release-Patch|x64
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x86.ActiveCfg = Release-Patch|Win32
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x86.Build.0 = Release-Patch|Win32
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2B}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2B}.Debug|x64.Build.0 = Debug|x64
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2B}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2B}.Debug|x86.Build.0 = Debug|Win32
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2B}.Release-Override|x64.ActiveCfg = Release-Override|x64
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2B}.Release-Override|x64.Build.0 = Release-Override|x64
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2B}.Release-Override|x86.ActiveCfg = Release-Override|Win32
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2B}.Release-Override|x86.Build.0 = Release-Override|Win32
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2B}.Release-Patch|x64.ActiveCfg = Release-Patch|x64
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2B}.Release-Patch|x64.Build.0 = Release-Patch|x64
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2B}.Release-Patch|x86.ActiveCfg = Release-Patch|Win32
|
||||
{9765198D-5305-4AB0-9A21-A0CD8201EB2B}.Release-Patch|x86.Build.0 = Release-Patch|Win32
|
||||
{4765198D-5305-4AB0-9A21-A0CD8201EB2A}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{4765198D-5305-4AB0-9A21-A0CD8201EB2A}.Debug|x64.Build.0 = Debug|x64
|
||||
{4765198D-5305-4AB0-9A21-A0CD8201EB2A}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{4765198D-5305-4AB0-9A21-A0CD8201EB2A}.Debug|x86.Build.0 = Debug|Win32
|
||||
{4765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Override|x64.ActiveCfg = Release-Override|x64
|
||||
{4765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Override|x64.Build.0 = Release-Override|x64
|
||||
{4765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Override|x86.ActiveCfg = Release-Override|Win32
|
||||
{4765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Override|x86.Build.0 = Release-Override|Win32
|
||||
{4765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x64.ActiveCfg = Release-Patch|x64
|
||||
{4765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x64.Build.0 = Release-Patch|x64
|
||||
{4765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x86.ActiveCfg = Release-Patch|Win32
|
||||
{4765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x86.Build.0 = Release-Patch|Win32
|
||||
{B765198D-5305-4AB0-9A21-A0CD8201EB2A}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{B765198D-5305-4AB0-9A21-A0CD8201EB2A}.Debug|x64.Build.0 = Debug|x64
|
||||
{B765198D-5305-4AB0-9A21-A0CD8201EB2A}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{B765198D-5305-4AB0-9A21-A0CD8201EB2A}.Debug|x86.Build.0 = Debug|Win32
|
||||
{B765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Override|x64.ActiveCfg = Release-Override|x64
|
||||
{B765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Override|x64.Build.0 = Release-Override|x64
|
||||
{B765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Override|x86.ActiveCfg = Release-Override|Win32
|
||||
{B765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Override|x86.Build.0 = Release-Override|Win32
|
||||
{B765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x64.ActiveCfg = Release-Patch|x64
|
||||
{B765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x64.Build.0 = Release-Patch|x64
|
||||
{B765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x86.ActiveCfg = Release-Patch|Win32
|
||||
{B765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x86.Build.0 = Release-Patch|Win32
|
||||
{A4754725-DE0D-4214-8979-324247AAD78E}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{A4754725-DE0D-4214-8979-324247AAD78E}.Debug|x64.Build.0 = Debug|x64
|
||||
{A4754725-DE0D-4214-8979-324247AAD78E}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{A4754725-DE0D-4214-8979-324247AAD78E}.Debug|x86.Build.0 = Debug|Win32
|
||||
{A4754725-DE0D-4214-8979-324247AAD78E}.Release-Override|x64.ActiveCfg = Release-Override|x64
|
||||
{A4754725-DE0D-4214-8979-324247AAD78E}.Release-Override|x64.Build.0 = Release-Override|x64
|
||||
{A4754725-DE0D-4214-8979-324247AAD78E}.Release-Override|x86.ActiveCfg = Release-Override|Win32
|
||||
{A4754725-DE0D-4214-8979-324247AAD78E}.Release-Override|x86.Build.0 = Release-Override|Win32
|
||||
{A4754725-DE0D-4214-8979-324247AAD78E}.Release-Patch|x64.ActiveCfg = Release-Patch|x64
|
||||
{A4754725-DE0D-4214-8979-324247AAD78E}.Release-Patch|x64.Build.0 = Release-Patch|x64
|
||||
{A4754725-DE0D-4214-8979-324247AAD78E}.Release-Patch|x86.ActiveCfg = Release-Patch|Win32
|
||||
{A4754725-DE0D-4214-8979-324247AAD78E}.Release-Patch|x86.Build.0 = Release-Patch|Win32
|
||||
{6CFFBD0F-09E3-4282-A711-0564451FDF74}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{6CFFBD0F-09E3-4282-A711-0564451FDF74}.Debug|x64.Build.0 = Debug|x64
|
||||
{6CFFBD0F-09E3-4282-A711-0564451FDF74}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{6CFFBD0F-09E3-4282-A711-0564451FDF74}.Debug|x86.Build.0 = Debug|Win32
|
||||
{6CFFBD0F-09E3-4282-A711-0564451FDF74}.Release-Override|x64.ActiveCfg = Release-Override|x64
|
||||
{6CFFBD0F-09E3-4282-A711-0564451FDF74}.Release-Override|x64.Build.0 = Release-Override|x64
|
||||
{6CFFBD0F-09E3-4282-A711-0564451FDF74}.Release-Override|x86.ActiveCfg = Release-Override|Win32
|
||||
{6CFFBD0F-09E3-4282-A711-0564451FDF74}.Release-Override|x86.Build.0 = Release-Override|Win32
|
||||
{6CFFBD0F-09E3-4282-A711-0564451FDF74}.Release-Patch|x64.ActiveCfg = Release-Patch|x64
|
||||
{6CFFBD0F-09E3-4282-A711-0564451FDF74}.Release-Patch|x64.Build.0 = Release-Patch|x64
|
||||
{6CFFBD0F-09E3-4282-A711-0564451FDF74}.Release-Patch|x86.ActiveCfg = Release-Patch|Win32
|
||||
{6CFFBD0F-09E3-4282-A711-0564451FDF74}.Release-Patch|x86.Build.0 = Release-Patch|Win32
|
||||
{5765198D-5305-4AB0-9A21-A0CD8201EB2A}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{5765198D-5305-4AB0-9A21-A0CD8201EB2A}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{5765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Override|x64.ActiveCfg = Release-Override|x64
|
||||
{5765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Override|x86.ActiveCfg = Release-Override|Win32
|
||||
{5765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x64.ActiveCfg = Release-Patch|x64
|
||||
{5765198D-5305-4AB0-9A21-A0CD8201EB2A}.Release-Patch|x86.ActiveCfg = Release-Patch|Win32
|
||||
{81CA712E-90B8-4AE5-9E89-5B436578D6DA}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{81CA712E-90B8-4AE5-9E89-5B436578D6DA}.Debug|x64.Build.0 = Debug|x64
|
||||
{81CA712E-90B8-4AE5-9E89-5B436578D6DA}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{81CA712E-90B8-4AE5-9E89-5B436578D6DA}.Debug|x86.Build.0 = Debug|Win32
|
||||
{81CA712E-90B8-4AE5-9E89-5B436578D6DA}.Release-Override|x64.ActiveCfg = Release-Override|x64
|
||||
{81CA712E-90B8-4AE5-9E89-5B436578D6DA}.Release-Override|x64.Build.0 = Release-Override|x64
|
||||
{81CA712E-90B8-4AE5-9E89-5B436578D6DA}.Release-Override|x86.ActiveCfg = Release-Override|Win32
|
||||
{81CA712E-90B8-4AE5-9E89-5B436578D6DA}.Release-Override|x86.Build.0 = Release-Override|Win32
|
||||
{81CA712E-90B8-4AE5-9E89-5B436578D6DA}.Release-Patch|x64.ActiveCfg = Release-Patch|x64
|
||||
{81CA712E-90B8-4AE5-9E89-5B436578D6DA}.Release-Patch|x64.Build.0 = Release-Patch|x64
|
||||
{81CA712E-90B8-4AE5-9E89-5B436578D6DA}.Release-Patch|x86.ActiveCfg = Release-Patch|Win32
|
||||
{81CA712E-90B8-4AE5-9E89-5B436578D6DA}.Release-Patch|x86.Build.0 = Release-Patch|Win32
|
||||
{3A559C75-FD26-4300-B86B-165FD43EE1CE}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{3A559C75-FD26-4300-B86B-165FD43EE1CE}.Debug|x64.Build.0 = Debug|x64
|
||||
{3A559C75-FD26-4300-B86B-165FD43EE1CE}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{3A559C75-FD26-4300-B86B-165FD43EE1CE}.Debug|x86.Build.0 = Debug|Win32
|
||||
{3A559C75-FD26-4300-B86B-165FD43EE1CE}.Release-Override|x64.ActiveCfg = Release-Override|x64
|
||||
{3A559C75-FD26-4300-B86B-165FD43EE1CE}.Release-Override|x64.Build.0 = Release-Override|x64
|
||||
{3A559C75-FD26-4300-B86B-165FD43EE1CE}.Release-Override|x86.ActiveCfg = Release-Override|Win32
|
||||
{3A559C75-FD26-4300-B86B-165FD43EE1CE}.Release-Override|x86.Build.0 = Release-Override|Win32
|
||||
{3A559C75-FD26-4300-B86B-165FD43EE1CE}.Release-Patch|x64.ActiveCfg = Release-Patch|x64
|
||||
{3A559C75-FD26-4300-B86B-165FD43EE1CE}.Release-Patch|x64.Build.0 = Release-Patch|x64
|
||||
{3A559C75-FD26-4300-B86B-165FD43EE1CE}.Release-Patch|x86.ActiveCfg = Release-Patch|Win32
|
||||
{3A559C75-FD26-4300-B86B-165FD43EE1CE}.Release-Patch|x86.Build.0 = Release-Patch|Win32
|
||||
{387F753A-0312-4A7B-A1D6-B2795E832E96}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{387F753A-0312-4A7B-A1D6-B2795E832E96}.Debug|x64.Build.0 = Debug|x64
|
||||
{387F753A-0312-4A7B-A1D6-B2795E832E96}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{387F753A-0312-4A7B-A1D6-B2795E832E96}.Debug|x86.Build.0 = Debug|Win32
|
||||
{387F753A-0312-4A7B-A1D6-B2795E832E96}.Release-Override|x64.ActiveCfg = Release-Override|x64
|
||||
{387F753A-0312-4A7B-A1D6-B2795E832E96}.Release-Override|x64.Build.0 = Release-Override|x64
|
||||
{387F753A-0312-4A7B-A1D6-B2795E832E96}.Release-Override|x86.ActiveCfg = Release-Override|Win32
|
||||
{387F753A-0312-4A7B-A1D6-B2795E832E96}.Release-Override|x86.Build.0 = Release-Override|Win32
|
||||
{387F753A-0312-4A7B-A1D6-B2795E832E96}.Release-Patch|x64.ActiveCfg = Release-Patch|x64
|
||||
{387F753A-0312-4A7B-A1D6-B2795E832E96}.Release-Patch|x64.Build.0 = Release-Patch|x64
|
||||
{387F753A-0312-4A7B-A1D6-B2795E832E96}.Release-Patch|x86.ActiveCfg = Release-Patch|Win32
|
||||
{387F753A-0312-4A7B-A1D6-B2795E832E96}.Release-Patch|x86.Build.0 = Release-Patch|Win32
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
EndGlobalSection
|
||||
EndGlobal
|
541
trunk/3rdparty/gperftools-2-fit/install-sh
vendored
Executable file
|
@ -0,0 +1,541 @@
|
|||
#!/bin/sh
|
||||
# install - install a program, script, or datafile
|
||||
|
||||
scriptversion=2020-11-14.01; # UTC
|
||||
|
||||
# This originates from X11R5 (mit/util/scripts/install.sh), which was
|
||||
# later released in X11R6 (xc/config/util/install.sh) with the
|
||||
# following copyright and license.
|
||||
#
|
||||
# Copyright (C) 1994 X Consortium
|
||||
#
|
||||
# Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
# of this software and associated documentation files (the "Software"), to
|
||||
# deal in the Software without restriction, including without limitation the
|
||||
# rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
|
||||
# sell copies of the Software, and to permit persons to whom the Software is
|
||||
# furnished to do so, subject to the following conditions:
|
||||
#
|
||||
# The above copyright notice and this permission notice shall be included in
|
||||
# all copies or substantial portions of the Software.
|
||||
#
|
||||
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
# X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
|
||||
# AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNEC-
|
||||
# TION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
#
|
||||
# Except as contained in this notice, the name of the X Consortium shall not
|
||||
# be used in advertising or otherwise to promote the sale, use or other deal-
|
||||
# ings in this Software without prior written authorization from the X Consor-
|
||||
# tium.
|
||||
#
|
||||
#
|
||||
# FSF changes to this file are in the public domain.
|
||||
#
|
||||
# Calling this script install-sh is preferred over install.sh, to prevent
|
||||
# 'make' implicit rules from creating a file called install from it
|
||||
# when there is no Makefile.
|
||||
#
|
||||
# This script is compatible with the BSD install script, but was written
|
||||
# from scratch.
|
||||
|
||||
tab=' '
|
||||
nl='
|
||||
'
|
||||
IFS=" $tab$nl"
|
||||
|
||||
# Set DOITPROG to "echo" to test this script.
|
||||
|
||||
doit=${DOITPROG-}
|
||||
doit_exec=${doit:-exec}
|
||||
|
||||
# Put in absolute file names if you don't have them in your path;
|
||||
# or use environment vars.
|
||||
|
||||
chgrpprog=${CHGRPPROG-chgrp}
|
||||
chmodprog=${CHMODPROG-chmod}
|
||||
chownprog=${CHOWNPROG-chown}
|
||||
cmpprog=${CMPPROG-cmp}
|
||||
cpprog=${CPPROG-cp}
|
||||
mkdirprog=${MKDIRPROG-mkdir}
|
||||
mvprog=${MVPROG-mv}
|
||||
rmprog=${RMPROG-rm}
|
||||
stripprog=${STRIPPROG-strip}
|
||||
|
||||
posix_mkdir=
|
||||
|
||||
# Desired mode of installed file.
|
||||
mode=0755
|
||||
|
||||
# Create dirs (including intermediate dirs) using mode 755.
|
||||
# This is like GNU 'install' as of coreutils 8.32 (2020).
|
||||
mkdir_umask=22
|
||||
|
||||
backupsuffix=
|
||||
chgrpcmd=
|
||||
chmodcmd=$chmodprog
|
||||
chowncmd=
|
||||
mvcmd=$mvprog
|
||||
rmcmd="$rmprog -f"
|
||||
stripcmd=
|
||||
|
||||
src=
|
||||
dst=
|
||||
dir_arg=
|
||||
dst_arg=
|
||||
|
||||
copy_on_change=false
|
||||
is_target_a_directory=possibly
|
||||
|
||||
usage="\
|
||||
Usage: $0 [OPTION]... [-T] SRCFILE DSTFILE
|
||||
or: $0 [OPTION]... SRCFILES... DIRECTORY
|
||||
or: $0 [OPTION]... -t DIRECTORY SRCFILES...
|
||||
or: $0 [OPTION]... -d DIRECTORIES...
|
||||
|
||||
In the 1st form, copy SRCFILE to DSTFILE.
|
||||
In the 2nd and 3rd, copy all SRCFILES to DIRECTORY.
|
||||
In the 4th, create DIRECTORIES.
|
||||
|
||||
Options:
|
||||
--help display this help and exit.
|
||||
--version display version info and exit.
|
||||
|
||||
-c (ignored)
|
||||
-C install only if different (preserve data modification time)
|
||||
-d create directories instead of installing files.
|
||||
-g GROUP $chgrpprog installed files to GROUP.
|
||||
-m MODE $chmodprog installed files to MODE.
|
||||
-o USER $chownprog installed files to USER.
|
||||
-p pass -p to $cpprog.
|
||||
-s $stripprog installed files.
|
||||
-S SUFFIX attempt to back up existing files, with suffix SUFFIX.
|
||||
-t DIRECTORY install into DIRECTORY.
|
||||
-T report an error if DSTFILE is a directory.
|
||||
|
||||
Environment variables override the default commands:
|
||||
CHGRPPROG CHMODPROG CHOWNPROG CMPPROG CPPROG MKDIRPROG MVPROG
|
||||
RMPROG STRIPPROG
|
||||
|
||||
By default, rm is invoked with -f; when overridden with RMPROG,
|
||||
it's up to you to specify -f if you want it.
|
||||
|
||||
If -S is not specified, no backups are attempted.
|
||||
|
||||
Email bug reports to bug-automake@gnu.org.
|
||||
Automake home page: https://www.gnu.org/software/automake/
|
||||
"
|
||||
|
||||
while test $# -ne 0; do
|
||||
case $1 in
|
||||
-c) ;;
|
||||
|
||||
-C) copy_on_change=true;;
|
||||
|
||||
-d) dir_arg=true;;
|
||||
|
||||
-g) chgrpcmd="$chgrpprog $2"
|
||||
shift;;
|
||||
|
||||
--help) echo "$usage"; exit $?;;
|
||||
|
||||
-m) mode=$2
|
||||
case $mode in
|
||||
*' '* | *"$tab"* | *"$nl"* | *'*'* | *'?'* | *'['*)
|
||||
echo "$0: invalid mode: $mode" >&2
|
||||
exit 1;;
|
||||
esac
|
||||
shift;;
|
||||
|
||||
-o) chowncmd="$chownprog $2"
|
||||
shift;;
|
||||
|
||||
-p) cpprog="$cpprog -p";;
|
||||
|
||||
-s) stripcmd=$stripprog;;
|
||||
|
||||
-S) backupsuffix="$2"
|
||||
shift;;
|
||||
|
||||
-t)
|
||||
is_target_a_directory=always
|
||||
dst_arg=$2
|
||||
# Protect names problematic for 'test' and other utilities.
|
||||
case $dst_arg in
|
||||
-* | [=\(\)!]) dst_arg=./$dst_arg;;
|
||||
esac
|
||||
shift;;
|
||||
|
||||
-T) is_target_a_directory=never;;
|
||||
|
||||
--version) echo "$0 $scriptversion"; exit $?;;
|
||||
|
||||
--) shift
|
||||
break;;
|
||||
|
||||
-*) echo "$0: invalid option: $1" >&2
|
||||
exit 1;;
|
||||
|
||||
*) break;;
|
||||
esac
|
||||
shift
|
||||
done
|
||||
|
||||
# We allow the use of options -d and -T together, by making -d
|
||||
# take the precedence; this is for compatibility with GNU install.
|
||||
|
||||
if test -n "$dir_arg"; then
|
||||
if test -n "$dst_arg"; then
|
||||
echo "$0: target directory not allowed when installing a directory." >&2
|
||||
exit 1
|
||||
fi
|
||||
fi
|
||||
|
||||
if test $# -ne 0 && test -z "$dir_arg$dst_arg"; then
|
||||
# When -d is used, all remaining arguments are directories to create.
|
||||
# When -t is used, the destination is already specified.
|
||||
# Otherwise, the last argument is the destination. Remove it from $@.
|
||||
for arg
|
||||
do
|
||||
if test -n "$dst_arg"; then
|
||||
# $@ is not empty: it contains at least $arg.
|
||||
set fnord "$@" "$dst_arg"
|
||||
shift # fnord
|
||||
fi
|
||||
shift # arg
|
||||
dst_arg=$arg
|
||||
# Protect names problematic for 'test' and other utilities.
|
||||
case $dst_arg in
|
||||
-* | [=\(\)!]) dst_arg=./$dst_arg;;
|
||||
esac
|
||||
done
|
||||
fi
|
||||
|
||||
if test $# -eq 0; then
|
||||
if test -z "$dir_arg"; then
|
||||
echo "$0: no input file specified." >&2
|
||||
exit 1
|
||||
fi
|
||||
# It's OK to call 'install-sh -d' without argument.
|
||||
# This can happen when creating conditional directories.
|
||||
exit 0
|
||||
fi
|
||||
|
||||
if test -z "$dir_arg"; then
|
||||
if test $# -gt 1 || test "$is_target_a_directory" = always; then
|
||||
if test ! -d "$dst_arg"; then
|
||||
echo "$0: $dst_arg: Is not a directory." >&2
|
||||
exit 1
|
||||
fi
|
||||
fi
|
||||
fi
|
||||
|
||||
if test -z "$dir_arg"; then
|
||||
do_exit='(exit $ret); exit $ret'
|
||||
trap "ret=129; $do_exit" 1
|
||||
trap "ret=130; $do_exit" 2
|
||||
trap "ret=141; $do_exit" 13
|
||||
trap "ret=143; $do_exit" 15
|
||||
|
||||
# Set umask so as not to create temps with too-generous modes.
|
||||
# However, 'strip' requires both read and write access to temps.
|
||||
case $mode in
|
||||
# Optimize common cases.
|
||||
*644) cp_umask=133;;
|
||||
*755) cp_umask=22;;
|
||||
|
||||
*[0-7])
|
||||
if test -z "$stripcmd"; then
|
||||
u_plus_rw=
|
||||
else
|
||||
u_plus_rw='% 200'
|
||||
fi
|
||||
cp_umask=`expr '(' 777 - $mode % 1000 ')' $u_plus_rw`;;
|
||||
*)
|
||||
if test -z "$stripcmd"; then
|
||||
u_plus_rw=
|
||||
else
|
||||
u_plus_rw=,u+rw
|
||||
fi
|
||||
cp_umask=$mode$u_plus_rw;;
|
||||
esac
|
||||
fi
|
||||
|
||||
for src
|
||||
do
|
||||
# Protect names problematic for 'test' and other utilities.
|
||||
case $src in
|
||||
-* | [=\(\)!]) src=./$src;;
|
||||
esac
|
||||
|
||||
if test -n "$dir_arg"; then
|
||||
dst=$src
|
||||
dstdir=$dst
|
||||
test -d "$dstdir"
|
||||
dstdir_status=$?
|
||||
# Don't chown directories that already exist.
|
||||
if test $dstdir_status = 0; then
|
||||
chowncmd=""
|
||||
fi
|
||||
else
|
||||
|
||||
# Waiting for this to be detected by the "$cpprog $src $dsttmp" command
|
||||
# might cause directories to be created, which would be especially bad
|
||||
# if $src (and thus $dsttmp) contains '*'.
|
||||
if test ! -f "$src" && test ! -d "$src"; then
|
||||
echo "$0: $src does not exist." >&2
|
||||
exit 1
|
||||
fi
|
||||
|
||||
if test -z "$dst_arg"; then
|
||||
echo "$0: no destination specified." >&2
|
||||
exit 1
|
||||
fi
|
||||
dst=$dst_arg
|
||||
|
||||
# If destination is a directory, append the input filename.
|
||||
if test -d "$dst"; then
|
||||
if test "$is_target_a_directory" = never; then
|
||||
echo "$0: $dst_arg: Is a directory" >&2
|
||||
exit 1
|
||||
fi
|
||||
dstdir=$dst
|
||||
dstbase=`basename "$src"`
|
||||
case $dst in
|
||||
*/) dst=$dst$dstbase;;
|
||||
*) dst=$dst/$dstbase;;
|
||||
esac
|
||||
dstdir_status=0
|
||||
else
|
||||
dstdir=`dirname "$dst"`
|
||||
test -d "$dstdir"
|
||||
dstdir_status=$?
|
||||
fi
|
||||
fi
|
||||
|
||||
case $dstdir in
|
||||
*/) dstdirslash=$dstdir;;
|
||||
*) dstdirslash=$dstdir/;;
|
||||
esac
|
||||
|
||||
obsolete_mkdir_used=false
|
||||
|
||||
if test $dstdir_status != 0; then
|
||||
case $posix_mkdir in
|
||||
'')
|
||||
# With -d, create the new directory with the user-specified mode.
|
||||
# Otherwise, rely on $mkdir_umask.
|
||||
if test -n "$dir_arg"; then
|
||||
mkdir_mode=-m$mode
|
||||
else
|
||||
mkdir_mode=
|
||||
fi
|
||||
|
||||
posix_mkdir=false
|
||||
# The $RANDOM variable is not portable (e.g., dash). Use it
|
||||
# here however when possible just to lower collision chance.
|
||||
tmpdir=${TMPDIR-/tmp}/ins$RANDOM-$$
|
||||
|
||||
trap '
|
||||
ret=$?
|
||||
rmdir "$tmpdir/a/b" "$tmpdir/a" "$tmpdir" 2>/dev/null
|
||||
exit $ret
|
||||
' 0
|
||||
|
||||
# Because "mkdir -p" follows existing symlinks and we likely work
|
||||
# directly in world-writeable /tmp, make sure that the '$tmpdir'
|
||||
# directory is successfully created first before we actually test
|
||||
# 'mkdir -p'.
|
||||
if (umask $mkdir_umask &&
|
||||
$mkdirprog $mkdir_mode "$tmpdir" &&
|
||||
exec $mkdirprog $mkdir_mode -p -- "$tmpdir/a/b") >/dev/null 2>&1
|
||||
then
|
||||
if test -z "$dir_arg" || {
|
||||
# Check for POSIX incompatibilities with -m.
|
||||
# HP-UX 11.23 and IRIX 6.5 mkdir -m -p sets group- or
|
||||
# other-writable bit of parent directory when it shouldn't.
|
||||
# FreeBSD 6.1 mkdir -m -p sets mode of existing directory.
|
||||
test_tmpdir="$tmpdir/a"
|
||||
ls_ld_tmpdir=`ls -ld "$test_tmpdir"`
|
||||
case $ls_ld_tmpdir in
|
||||
d????-?r-*) different_mode=700;;
|
||||
d????-?--*) different_mode=755;;
|
||||
*) false;;
|
||||
esac &&
|
||||
$mkdirprog -m$different_mode -p -- "$test_tmpdir" && {
|
||||
ls_ld_tmpdir_1=`ls -ld "$test_tmpdir"`
|
||||
test "$ls_ld_tmpdir" = "$ls_ld_tmpdir_1"
|
||||
}
|
||||
}
|
||||
then posix_mkdir=:
|
||||
fi
|
||||
rmdir "$tmpdir/a/b" "$tmpdir/a" "$tmpdir"
|
||||
else
|
||||
# Remove any dirs left behind by ancient mkdir implementations.
|
||||
rmdir ./$mkdir_mode ./-p ./-- "$tmpdir" 2>/dev/null
|
||||
fi
|
||||
trap '' 0;;
|
||||
esac
|
||||
|
||||
if
|
||||
$posix_mkdir && (
|
||||
umask $mkdir_umask &&
|
||||
$doit_exec $mkdirprog $mkdir_mode -p -- "$dstdir"
|
||||
)
|
||||
then :
|
||||
else
|
||||
|
||||
# mkdir does not conform to POSIX,
|
||||
# or it failed possibly due to a race condition. Create the
|
||||
# directory the slow way, step by step, checking for races as we go.
|
||||
|
||||
case $dstdir in
|
||||
/*) prefix='/';;
|
||||
[-=\(\)!]*) prefix='./';;
|
||||
*) prefix='';;
|
||||
esac
|
||||
|
||||
oIFS=$IFS
|
||||
IFS=/
|
||||
set -f
|
||||
set fnord $dstdir
|
||||
shift
|
||||
set +f
|
||||
IFS=$oIFS
|
||||
|
||||
prefixes=
|
||||
|
||||
for d
|
||||
do
|
||||
test X"$d" = X && continue
|
||||
|
||||
prefix=$prefix$d
|
||||
if test -d "$prefix"; then
|
||||
prefixes=
|
||||
else
|
||||
if $posix_mkdir; then
|
||||
(umask $mkdir_umask &&
|
||||
$doit_exec $mkdirprog $mkdir_mode -p -- "$dstdir") && break
|
||||
# Don't fail if two instances are running concurrently.
|
||||
test -d "$prefix" || exit 1
|
||||
else
|
||||
case $prefix in
|
||||
*\'*) qprefix=`echo "$prefix" | sed "s/'/'\\\\\\\\''/g"`;;
|
||||
*) qprefix=$prefix;;
|
||||
esac
|
||||
prefixes="$prefixes '$qprefix'"
|
||||
fi
|
||||
fi
|
||||
prefix=$prefix/
|
||||
done
|
||||
|
||||
if test -n "$prefixes"; then
|
||||
# Don't fail if two instances are running concurrently.
|
||||
(umask $mkdir_umask &&
|
||||
eval "\$doit_exec \$mkdirprog $prefixes") ||
|
||||
test -d "$dstdir" || exit 1
|
||||
obsolete_mkdir_used=true
|
||||
fi
|
||||
fi
|
||||
fi
|
||||
|
||||
if test -n "$dir_arg"; then
|
||||
{ test -z "$chowncmd" || $doit $chowncmd "$dst"; } &&
|
||||
{ test -z "$chgrpcmd" || $doit $chgrpcmd "$dst"; } &&
|
||||
{ test "$obsolete_mkdir_used$chowncmd$chgrpcmd" = false ||
|
||||
test -z "$chmodcmd" || $doit $chmodcmd $mode "$dst"; } || exit 1
|
||||
else
|
||||
|
||||
# Make a couple of temp file names in the proper directory.
|
||||
dsttmp=${dstdirslash}_inst.$$_
|
||||
rmtmp=${dstdirslash}_rm.$$_
|
||||
|
||||
# Trap to clean up those temp files at exit.
|
||||
trap 'ret=$?; rm -f "$dsttmp" "$rmtmp" && exit $ret' 0
|
||||
|
||||
# Copy the file name to the temp name.
|
||||
(umask $cp_umask &&
|
||||
{ test -z "$stripcmd" || {
|
||||
# Create $dsttmp read-write so that cp doesn't create it read-only,
|
||||
# which would cause strip to fail.
|
||||
if test -z "$doit"; then
|
||||
: >"$dsttmp" # No need to fork-exec 'touch'.
|
||||
else
|
||||
$doit touch "$dsttmp"
|
||||
fi
|
||||
}
|
||||
} &&
|
||||
$doit_exec $cpprog "$src" "$dsttmp") &&
|
||||
|
||||
# and set any options; do chmod last to preserve setuid bits.
|
||||
#
|
||||
# If any of these fail, we abort the whole thing. If we want to
|
||||
# ignore errors from any of these, just make sure not to ignore
|
||||
# errors from the above "$doit $cpprog $src $dsttmp" command.
|
||||
#
|
||||
{ test -z "$chowncmd" || $doit $chowncmd "$dsttmp"; } &&
|
||||
{ test -z "$chgrpcmd" || $doit $chgrpcmd "$dsttmp"; } &&
|
||||
{ test -z "$stripcmd" || $doit $stripcmd "$dsttmp"; } &&
|
||||
{ test -z "$chmodcmd" || $doit $chmodcmd $mode "$dsttmp"; } &&
|
||||
|
||||
# If -C, don't bother to copy if it wouldn't change the file.
|
||||
if $copy_on_change &&
|
||||
old=`LC_ALL=C ls -dlL "$dst" 2>/dev/null` &&
|
||||
new=`LC_ALL=C ls -dlL "$dsttmp" 2>/dev/null` &&
|
||||
set -f &&
|
||||
set X $old && old=:$2:$4:$5:$6 &&
|
||||
set X $new && new=:$2:$4:$5:$6 &&
|
||||
set +f &&
|
||||
test "$old" = "$new" &&
|
||||
$cmpprog "$dst" "$dsttmp" >/dev/null 2>&1
|
||||
then
|
||||
rm -f "$dsttmp"
|
||||
else
|
||||
# If $backupsuffix is set, and the file being installed
|
||||
# already exists, attempt a backup. Don't worry if it fails,
|
||||
# e.g., if mv doesn't support -f.
|
||||
if test -n "$backupsuffix" && test -f "$dst"; then
|
||||
$doit $mvcmd -f "$dst" "$dst$backupsuffix" 2>/dev/null
|
||||
fi
|
||||
|
||||
# Rename the file to the real destination.
|
||||
$doit $mvcmd -f "$dsttmp" "$dst" 2>/dev/null ||
|
||||
|
||||
# The rename failed, perhaps because mv can't rename something else
|
||||
# to itself, or perhaps because mv is so ancient that it does not
|
||||
# support -f.
|
||||
{
|
||||
# Now remove or move aside any old file at destination location.
|
||||
# We try this two ways since rm can't unlink itself on some
|
||||
# systems and the destination file might be busy for other
|
||||
# reasons. In this case, the final cleanup might fail but the new
|
||||
# file should still install successfully.
|
||||
{
|
||||
test ! -f "$dst" ||
|
||||
$doit $rmcmd "$dst" 2>/dev/null ||
|
||||
{ $doit $mvcmd -f "$dst" "$rmtmp" 2>/dev/null &&
|
||||
{ $doit $rmcmd "$rmtmp" 2>/dev/null; :; }
|
||||
} ||
|
||||
{ echo "$0: cannot unlink or rename $dst" >&2
|
||||
(exit 1); exit 1
|
||||
}
|
||||
} &&
|
||||
|
||||
# Now rename the file to the real destination.
|
||||
$doit $mvcmd "$dsttmp" "$dst"
|
||||
}
|
||||
fi || exit 1
|
||||
|
||||
trap '' 0
|
||||
fi
|
||||
done
|
||||
|
||||
# Local variables:
|
||||
# eval: (add-hook 'before-save-hook 'time-stamp)
|
||||
# time-stamp-start: "scriptversion="
|
||||
# time-stamp-format: "%:y-%02m-%02d.%02H"
|
||||
# time-stamp-time-zone: "UTC0"
|
||||
# time-stamp-end: "; # UTC"
|
||||
# End:
|
11911
trunk/3rdparty/gperftools-2-fit/libtool
vendored
Executable file
11251
trunk/3rdparty/gperftools-2-fit/ltmain.sh
vendored
Executable file
16
trunk/3rdparty/gperftools-2-fit/m4/ac_have_attribute.m4
vendored
Normal file
|
@ -0,0 +1,16 @@
|
|||
AC_DEFUN([AX_C___ATTRIBUTE__], [
|
||||
AC_MSG_CHECKING(for __attribute__)
|
||||
AC_CACHE_VAL(ac_cv___attribute__, [
|
||||
AC_TRY_COMPILE(
|
||||
[#include <stdlib.h>
|
||||
static void foo(void) __attribute__ ((unused));
|
||||
void foo(void) { exit(1); }],
|
||||
[],
|
||||
ac_cv___attribute__=yes,
|
||||
ac_cv___attribute__=no
|
||||
)])
|
||||
if test "$ac_cv___attribute__" = "yes"; then
|
||||
AC_DEFINE(HAVE___ATTRIBUTE__, 1, [define if your compiler has __attribute__])
|
||||
fi
|
||||
AC_MSG_RESULT($ac_cv___attribute__)
|
||||
])
|
35
trunk/3rdparty/gperftools-2-fit/m4/acx_nanosleep.m4
vendored
Normal file
|
@ -0,0 +1,35 @@
|
|||
# Check for support for nanosleep. It's defined in <time.h>, but on
|
||||
# some systems, such as solaris, you need to link in a library to use it.
|
||||
# We set acx_nanosleep_ok if nanosleep is supported; in that case,
|
||||
# NANOSLEEP_LIBS is set to whatever libraries are needed to support
|
||||
# nanosleep.
|
||||
|
||||
AC_DEFUN([ACX_NANOSLEEP],
|
||||
[AC_MSG_CHECKING(if nanosleep requires any libraries)
|
||||
AC_LANG_SAVE
|
||||
AC_LANG_C
|
||||
acx_nanosleep_ok="no"
|
||||
NANOSLEEP_LIBS=
|
||||
# For most folks, this should just work
|
||||
AC_TRY_LINK([#include <time.h>],
|
||||
[static struct timespec ts; nanosleep(&ts, NULL);],
|
||||
[acx_nanosleep_ok=yes])
|
||||
# For solaris, we may need -lrt
|
||||
if test "x$acx_nanosleep_ok" != "xyes"; then
|
||||
OLD_LIBS="$LIBS"
|
||||
LIBS="-lrt $LIBS"
|
||||
AC_TRY_LINK([#include <time.h>],
|
||||
[static struct timespec ts; nanosleep(&ts, NULL);],
|
||||
[acx_nanosleep_ok=yes])
|
||||
if test "x$acx_nanosleep_ok" = "xyes"; then
|
||||
NANOSLEEP_LIBS="-lrt"
|
||||
fi
|
||||
LIBS="$OLD_LIBS"
|
||||
fi
|
||||
if test "x$acx_nanosleep_ok" != "xyes"; then
|
||||
AC_MSG_ERROR([cannot find the nanosleep function])
|
||||
else
|
||||
AC_MSG_RESULT(${NANOSLEEP_LIBS:-no})
|
||||
fi
|
||||
AC_LANG_RESTORE
|
||||
])
|
397
trunk/3rdparty/gperftools-2-fit/m4/acx_pthread.m4
vendored
Normal file
|
@ -0,0 +1,397 @@
|
|||
# This was retrieved from
|
||||
# http://svn.0pointer.de/viewvc/trunk/common/acx_pthread.m4?revision=1277&root=avahi
|
||||
# See also (perhaps for new versions?)
|
||||
# http://svn.0pointer.de/viewvc/trunk/common/acx_pthread.m4?root=avahi
|
||||
#
|
||||
# We've rewritten the inconsistency check code (from avahi), to work
|
||||
# more broadly. In particular, it no longer assumes ld accepts -zdefs.
|
||||
# This caused a restructing of the code, but the functionality has only
|
||||
# changed a little.
|
||||
|
||||
dnl @synopsis ACX_PTHREAD([ACTION-IF-FOUND[, ACTION-IF-NOT-FOUND]])
|
||||
dnl
|
||||
dnl @summary figure out how to build C programs using POSIX threads
|
||||
dnl
|
||||
dnl This macro figures out how to build C programs using POSIX threads.
|
||||
dnl It sets the PTHREAD_LIBS output variable to the threads library and
|
||||
dnl linker flags, and the PTHREAD_CFLAGS output variable to any special
|
||||
dnl C compiler flags that are needed. (The user can also force certain
|
||||
dnl compiler flags/libs to be tested by setting these environment
|
||||
dnl variables.)
|
||||
dnl
|
||||
dnl Also sets PTHREAD_CC to any special C compiler that is needed for
|
||||
dnl multi-threaded programs (defaults to the value of CC otherwise).
|
||||
dnl (This is necessary on AIX to use the special cc_r compiler alias.)
|
||||
dnl
|
||||
dnl NOTE: You are assumed to not only compile your program with these
|
||||
dnl flags, but also link it with them as well. e.g. you should link
|
||||
dnl with $PTHREAD_CC $CFLAGS $PTHREAD_CFLAGS $LDFLAGS ... $PTHREAD_LIBS
|
||||
dnl $LIBS
|
||||
dnl
|
||||
dnl If you are only building threads programs, you may wish to use
|
||||
dnl these variables in your default LIBS, CFLAGS, and CC:
|
||||
dnl
|
||||
dnl LIBS="$PTHREAD_LIBS $LIBS"
|
||||
dnl CFLAGS="$CFLAGS $PTHREAD_CFLAGS"
|
||||
dnl CC="$PTHREAD_CC"
|
||||
dnl
|
||||
dnl In addition, if the PTHREAD_CREATE_JOINABLE thread-attribute
|
||||
dnl constant has a nonstandard name, defines PTHREAD_CREATE_JOINABLE to
|
||||
dnl that name (e.g. PTHREAD_CREATE_UNDETACHED on AIX).
|
||||
dnl
|
||||
dnl ACTION-IF-FOUND is a list of shell commands to run if a threads
|
||||
dnl library is found, and ACTION-IF-NOT-FOUND is a list of commands to
|
||||
dnl run it if it is not found. If ACTION-IF-FOUND is not specified, the
|
||||
dnl default action will define HAVE_PTHREAD.
|
||||
dnl
|
||||
dnl Please let the authors know if this macro fails on any platform, or
|
||||
dnl if you have any other suggestions or comments. This macro was based
|
||||
dnl on work by SGJ on autoconf scripts for FFTW (www.fftw.org) (with
|
||||
dnl help from M. Frigo), as well as ac_pthread and hb_pthread macros
|
||||
dnl posted by Alejandro Forero Cuervo to the autoconf macro repository.
|
||||
dnl We are also grateful for the helpful feedback of numerous users.
|
||||
dnl
|
||||
dnl @category InstalledPackages
|
||||
dnl @author Steven G. Johnson <stevenj@alum.mit.edu>
|
||||
dnl @version 2006-05-29
|
||||
dnl @license GPLWithACException
|
||||
dnl
|
||||
dnl Checks for GCC shared/pthread inconsistency based on work by
|
||||
dnl Marcin Owsiany <marcin@owsiany.pl>
|
||||
|
||||
|
||||
AC_DEFUN([ACX_PTHREAD], [
|
||||
AC_REQUIRE([AC_CANONICAL_HOST])
|
||||
AC_LANG_SAVE
|
||||
AC_LANG_C
|
||||
acx_pthread_ok=no
|
||||
|
||||
# We used to check for pthread.h first, but this fails if pthread.h
|
||||
# requires special compiler flags (e.g. on True64 or Sequent).
|
||||
# It gets checked for in the link test anyway.
|
||||
|
||||
# First of all, check if the user has set any of the PTHREAD_LIBS,
|
||||
# etcetera environment variables, and if threads linking works using
|
||||
# them:
|
||||
if test x"$PTHREAD_LIBS$PTHREAD_CFLAGS" != x; then
|
||||
save_CFLAGS="$CFLAGS"
|
||||
CFLAGS="$CFLAGS $PTHREAD_CFLAGS"
|
||||
save_LIBS="$LIBS"
|
||||
LIBS="$PTHREAD_LIBS $LIBS"
|
||||
AC_MSG_CHECKING([for pthread_join in LIBS=$PTHREAD_LIBS with CFLAGS=$PTHREAD_CFLAGS])
|
||||
AC_TRY_LINK_FUNC(pthread_join, acx_pthread_ok=yes)
|
||||
AC_MSG_RESULT($acx_pthread_ok)
|
||||
if test x"$acx_pthread_ok" = xno; then
|
||||
PTHREAD_LIBS=""
|
||||
PTHREAD_CFLAGS=""
|
||||
fi
|
||||
LIBS="$save_LIBS"
|
||||
CFLAGS="$save_CFLAGS"
|
||||
fi
|
||||
|
||||
# We must check for the threads library under a number of different
|
||||
# names; the ordering is very important because some systems
|
||||
# (e.g. DEC) have both -lpthread and -lpthreads, where one of the
|
||||
# libraries is broken (non-POSIX).
|
||||
|
||||
# Create a list of thread flags to try. Items starting with a "-" are
|
||||
# C compiler flags, and other items are library names, except for "none"
|
||||
# which indicates that we try without any flags at all, and "pthread-config"
|
||||
# which is a program returning the flags for the Pth emulation library.
|
||||
|
||||
acx_pthread_flags="pthreads none -Kthread -kthread lthread -pthread -pthreads -mthreads pthread --thread-safe -mt pthread-config"
|
||||
|
||||
# The ordering *is* (sometimes) important. Some notes on the
|
||||
# individual items follow:
|
||||
|
||||
# pthreads: AIX (must check this before -lpthread)
|
||||
# none: in case threads are in libc; should be tried before -Kthread and
|
||||
# other compiler flags to prevent continual compiler warnings
|
||||
# -Kthread: Sequent (threads in libc, but -Kthread needed for pthread.h)
|
||||
# -kthread: FreeBSD kernel threads (preferred to -pthread since SMP-able)
|
||||
# lthread: LinuxThreads port on FreeBSD (also preferred to -pthread)
|
||||
# -pthread: Linux/gcc (kernel threads), BSD/gcc (userland threads)
|
||||
# -pthreads: Solaris/gcc
|
||||
# -mthreads: Mingw32/gcc, Lynx/gcc
|
||||
# -mt: Sun Workshop C (may only link SunOS threads [-lthread], but it
|
||||
# doesn't hurt to check since this sometimes defines pthreads too;
|
||||
# also defines -D_REENTRANT)
|
||||
# ... -mt is also the pthreads flag for HP/aCC
|
||||
# pthread: Linux, etcetera
|
||||
# --thread-safe: KAI C++
|
||||
# pthread-config: use pthread-config program (for GNU Pth library)
|
||||
|
||||
case "${host_cpu}-${host_os}" in
|
||||
*solaris*)
|
||||
|
||||
# On Solaris (at least, for some versions), libc contains stubbed
|
||||
# (non-functional) versions of the pthreads routines, so link-based
|
||||
# tests will erroneously succeed. (We need to link with -pthreads/-mt/
|
||||
# -lpthread.) (The stubs are missing pthread_cleanup_push, or rather
|
||||
# a function called by this macro, so we could check for that, but
|
||||
# who knows whether they'll stub that too in a future libc.) So,
|
||||
# we'll just look for -pthreads and -lpthread first:
|
||||
|
||||
acx_pthread_flags="-pthreads pthread -mt -pthread $acx_pthread_flags"
|
||||
;;
|
||||
esac
|
||||
|
||||
if test x"$acx_pthread_ok" = xno; then
|
||||
for flag in $acx_pthread_flags; do
|
||||
|
||||
case $flag in
|
||||
none)
|
||||
AC_MSG_CHECKING([whether pthreads work without any flags])
|
||||
;;
|
||||
|
||||
-*)
|
||||
AC_MSG_CHECKING([whether pthreads work with $flag])
|
||||
PTHREAD_CFLAGS="$flag"
|
||||
;;
|
||||
|
||||
pthread-config)
|
||||
AC_CHECK_PROG(acx_pthread_config, pthread-config, yes, no)
|
||||
if test x"$acx_pthread_config" = xno; then continue; fi
|
||||
PTHREAD_CFLAGS="`pthread-config --cflags`"
|
||||
PTHREAD_LIBS="`pthread-config --ldflags` `pthread-config --libs`"
|
||||
;;
|
||||
|
||||
*)
|
||||
AC_MSG_CHECKING([for the pthreads library -l$flag])
|
||||
PTHREAD_LIBS="-l$flag"
|
||||
;;
|
||||
esac
|
||||
|
||||
save_LIBS="$LIBS"
|
||||
save_CFLAGS="$CFLAGS"
|
||||
LIBS="$PTHREAD_LIBS $LIBS"
|
||||
CFLAGS="$CFLAGS $PTHREAD_CFLAGS"
|
||||
|
||||
# Check for various functions. We must include pthread.h,
|
||||
# since some functions may be macros. (On the Sequent, we
|
||||
# need a special flag -Kthread to make this header compile.)
|
||||
# We check for pthread_join because it is in -lpthread on IRIX
|
||||
# while pthread_create is in libc. We check for pthread_attr_init
|
||||
# due to DEC craziness with -lpthreads. We check for
|
||||
# pthread_cleanup_push because it is one of the few pthread
|
||||
# functions on Solaris that doesn't have a non-functional libc stub.
|
||||
# We try pthread_create on general principles.
|
||||
AC_TRY_LINK([#include <pthread.h>],
|
||||
[pthread_t th; pthread_join(th, 0);
|
||||
pthread_attr_init(0); pthread_cleanup_push(0, 0);
|
||||
pthread_create(0,0,0,0); pthread_cleanup_pop(0); ],
|
||||
[acx_pthread_ok=yes])
|
||||
|
||||
LIBS="$save_LIBS"
|
||||
CFLAGS="$save_CFLAGS"
|
||||
|
||||
AC_MSG_RESULT($acx_pthread_ok)
|
||||
if test "x$acx_pthread_ok" = xyes; then
|
||||
break;
|
||||
fi
|
||||
|
||||
PTHREAD_LIBS=""
|
||||
PTHREAD_CFLAGS=""
|
||||
done
|
||||
fi
|
||||
|
||||
# Various other checks:
|
||||
if test "x$acx_pthread_ok" = xyes; then
|
||||
save_LIBS="$LIBS"
|
||||
LIBS="$PTHREAD_LIBS $LIBS"
|
||||
save_CFLAGS="$CFLAGS"
|
||||
CFLAGS="$CFLAGS $PTHREAD_CFLAGS"
|
||||
|
||||
# Detect AIX lossage: JOINABLE attribute is called UNDETACHED.
|
||||
AC_MSG_CHECKING([for joinable pthread attribute])
|
||||
attr_name=unknown
|
||||
for attr in PTHREAD_CREATE_JOINABLE PTHREAD_CREATE_UNDETACHED; do
|
||||
AC_TRY_LINK([#include <pthread.h>], [int attr=$attr; return attr;],
|
||||
[attr_name=$attr; break])
|
||||
done
|
||||
AC_MSG_RESULT($attr_name)
|
||||
if test "$attr_name" != PTHREAD_CREATE_JOINABLE; then
|
||||
AC_DEFINE_UNQUOTED(PTHREAD_CREATE_JOINABLE, $attr_name,
|
||||
[Define to necessary symbol if this constant
|
||||
uses a non-standard name on your system.])
|
||||
fi
|
||||
|
||||
AC_MSG_CHECKING([if more special flags are required for pthreads])
|
||||
flag=no
|
||||
case "${host_cpu}-${host_os}" in
|
||||
*-aix* | *-freebsd* | *-darwin*) flag="-D_THREAD_SAFE";;
|
||||
*solaris* | *-osf* | *-hpux*) flag="-D_REENTRANT";;
|
||||
esac
|
||||
AC_MSG_RESULT(${flag})
|
||||
if test "x$flag" != xno; then
|
||||
PTHREAD_CFLAGS="$flag $PTHREAD_CFLAGS"
|
||||
fi
|
||||
|
||||
LIBS="$save_LIBS"
|
||||
CFLAGS="$save_CFLAGS"
|
||||
# More AIX lossage: must compile with xlc_r or cc_r
|
||||
if test x"$GCC" != xyes; then
|
||||
AC_CHECK_PROGS(PTHREAD_CC, xlc_r cc_r, ${CC})
|
||||
else
|
||||
PTHREAD_CC=$CC
|
||||
fi
|
||||
|
||||
# The next part tries to detect GCC inconsistency with -shared on some
|
||||
# architectures and systems. The problem is that in certain
|
||||
# configurations, when -shared is specified, GCC "forgets" to
|
||||
# internally use various flags which are still necessary.
|
||||
|
||||
#
|
||||
# Prepare the flags
|
||||
#
|
||||
save_CFLAGS="$CFLAGS"
|
||||
save_LIBS="$LIBS"
|
||||
save_CC="$CC"
|
||||
|
||||
# Try with the flags determined by the earlier checks.
|
||||
#
|
||||
# -Wl,-z,defs forces link-time symbol resolution, so that the
|
||||
# linking checks with -shared actually have any value
|
||||
#
|
||||
# FIXME: -fPIC is required for -shared on many architectures,
|
||||
# so we specify it here, but the right way would probably be to
|
||||
# properly detect whether it is actually required.
|
||||
CFLAGS="-shared -fPIC -Wl,-z,defs $CFLAGS $PTHREAD_CFLAGS"
|
||||
LIBS="$PTHREAD_LIBS $LIBS"
|
||||
CC="$PTHREAD_CC"
|
||||
|
||||
# In order not to create several levels of indentation, we test
|
||||
# the value of "$done" until we find the cure or run out of ideas.
|
||||
done="no"
|
||||
|
||||
# First, make sure the CFLAGS we added are actually accepted by our
|
||||
# compiler. If not (and OS X's ld, for instance, does not accept -z),
|
||||
# then we can't do this test.
|
||||
if test x"$done" = xno; then
|
||||
AC_MSG_CHECKING([whether to check for GCC pthread/shared inconsistencies])
|
||||
AC_TRY_LINK(,, , [done=yes])
|
||||
|
||||
if test "x$done" = xyes ; then
|
||||
AC_MSG_RESULT([no])
|
||||
else
|
||||
AC_MSG_RESULT([yes])
|
||||
fi
|
||||
fi
|
||||
|
||||
if test x"$done" = xno; then
|
||||
AC_MSG_CHECKING([whether -pthread is sufficient with -shared])
|
||||
AC_TRY_LINK([#include <pthread.h>],
|
||||
[pthread_t th; pthread_join(th, 0);
|
||||
pthread_attr_init(0); pthread_cleanup_push(0, 0);
|
||||
pthread_create(0,0,0,0); pthread_cleanup_pop(0); ],
|
||||
[done=yes])
|
||||
|
||||
if test "x$done" = xyes; then
|
||||
AC_MSG_RESULT([yes])
|
||||
else
|
||||
AC_MSG_RESULT([no])
|
||||
fi
|
||||
fi
|
||||
|
||||
#
|
||||
# Linux gcc on some architectures such as mips/mipsel forgets
|
||||
# about -lpthread
|
||||
#
|
||||
if test x"$done" = xno; then
|
||||
AC_MSG_CHECKING([whether -lpthread fixes that])
|
||||
LIBS="-lpthread $PTHREAD_LIBS $save_LIBS"
|
||||
AC_TRY_LINK([#include <pthread.h>],
|
||||
[pthread_t th; pthread_join(th, 0);
|
||||
pthread_attr_init(0); pthread_cleanup_push(0, 0);
|
||||
pthread_create(0,0,0,0); pthread_cleanup_pop(0); ],
|
||||
[done=yes])
|
||||
|
||||
if test "x$done" = xyes; then
|
||||
AC_MSG_RESULT([yes])
|
||||
PTHREAD_LIBS="-lpthread $PTHREAD_LIBS"
|
||||
else
|
||||
AC_MSG_RESULT([no])
|
||||
fi
|
||||
fi
|
||||
#
|
||||
# FreeBSD 4.10 gcc forgets to use -lc_r instead of -lc
|
||||
#
|
||||
if test x"$done" = xno; then
|
||||
AC_MSG_CHECKING([whether -lc_r fixes that])
|
||||
LIBS="-lc_r $PTHREAD_LIBS $save_LIBS"
|
||||
AC_TRY_LINK([#include <pthread.h>],
|
||||
[pthread_t th; pthread_join(th, 0);
|
||||
pthread_attr_init(0); pthread_cleanup_push(0, 0);
|
||||
pthread_create(0,0,0,0); pthread_cleanup_pop(0); ],
|
||||
[done=yes])
|
||||
|
||||
if test "x$done" = xyes; then
|
||||
AC_MSG_RESULT([yes])
|
||||
PTHREAD_LIBS="-lc_r $PTHREAD_LIBS"
|
||||
else
|
||||
AC_MSG_RESULT([no])
|
||||
fi
|
||||
fi
|
||||
if test x"$done" = xno; then
|
||||
# OK, we have run out of ideas
|
||||
AC_MSG_WARN([Impossible to determine how to use pthreads with shared libraries])
|
||||
|
||||
# so it's not safe to assume that we may use pthreads
|
||||
acx_pthread_ok=no
|
||||
fi
|
||||
|
||||
AC_MSG_CHECKING([whether what we have so far is sufficient with -nostdlib])
|
||||
CFLAGS="-nostdlib $CFLAGS"
|
||||
# we need c with nostdlib
|
||||
LIBS="$LIBS -lc"
|
||||
AC_TRY_LINK([#include <pthread.h>],
|
||||
[pthread_t th; pthread_join(th, 0);
|
||||
pthread_attr_init(0); pthread_cleanup_push(0, 0);
|
||||
pthread_create(0,0,0,0); pthread_cleanup_pop(0); ],
|
||||
[done=yes],[done=no])
|
||||
|
||||
if test "x$done" = xyes; then
|
||||
AC_MSG_RESULT([yes])
|
||||
else
|
||||
AC_MSG_RESULT([no])
|
||||
fi
|
||||
|
||||
if test x"$done" = xno; then
|
||||
AC_MSG_CHECKING([whether -lpthread saves the day])
|
||||
LIBS="-lpthread $LIBS"
|
||||
AC_TRY_LINK([#include <pthread.h>],
|
||||
[pthread_t th; pthread_join(th, 0);
|
||||
pthread_attr_init(0); pthread_cleanup_push(0, 0);
|
||||
pthread_create(0,0,0,0); pthread_cleanup_pop(0); ],
|
||||
[done=yes],[done=no])
|
||||
|
||||
if test "x$done" = xyes; then
|
||||
AC_MSG_RESULT([yes])
|
||||
PTHREAD_LIBS="$PTHREAD_LIBS -lpthread"
|
||||
else
|
||||
AC_MSG_RESULT([no])
|
||||
AC_MSG_WARN([Impossible to determine how to use pthreads with shared libraries and -nostdlib])
|
||||
fi
|
||||
fi
|
||||
|
||||
CFLAGS="$save_CFLAGS"
|
||||
LIBS="$save_LIBS"
|
||||
CC="$save_CC"
|
||||
else
|
||||
PTHREAD_CC="$CC"
|
||||
fi
|
||||
|
||||
AC_SUBST(PTHREAD_LIBS)
|
||||
AC_SUBST(PTHREAD_CFLAGS)
|
||||
AC_SUBST(PTHREAD_CC)
|
||||
|
||||
# Finally, execute ACTION-IF-FOUND/ACTION-IF-NOT-FOUND:
|
||||
if test x"$acx_pthread_ok" = xyes; then
|
||||
ifelse([$1],,AC_DEFINE(HAVE_PTHREAD,1,[Define if you have POSIX threads libraries and header files.]),[$1])
|
||||
:
|
||||
else
|
||||
acx_pthread_ok=no
|
||||
$2
|
||||
fi
|
||||
AC_LANG_RESTORE
|
||||
])dnl ACX_PTHREAD
|
948
trunk/3rdparty/gperftools-2-fit/m4/ax_cxx_compile_stdcxx.m4
vendored
Normal file
|
@ -0,0 +1,948 @@
|
|||
# ===========================================================================
|
||||
# https://www.gnu.org/software/autoconf-archive/ax_cxx_compile_stdcxx.html
|
||||
# ===========================================================================
|
||||
#
|
||||
# SYNOPSIS
|
||||
#
|
||||
# AX_CXX_COMPILE_STDCXX(VERSION, [ext|noext], [mandatory|optional])
|
||||
#
|
||||
# DESCRIPTION
|
||||
#
|
||||
# Check for baseline language coverage in the compiler for the specified
|
||||
# version of the C++ standard. If necessary, add switches to CXX and
|
||||
# CXXCPP to enable support. VERSION may be '11' (for the C++11 standard)
|
||||
# or '14' (for the C++14 standard).
|
||||
#
|
||||
# The second argument, if specified, indicates whether you insist on an
|
||||
# extended mode (e.g. -std=gnu++11) or a strict conformance mode (e.g.
|
||||
# -std=c++11). If neither is specified, you get whatever works, with
|
||||
# preference for an extended mode.
|
||||
#
|
||||
# The third argument, if specified 'mandatory' or if left unspecified,
|
||||
# indicates that baseline support for the specified C++ standard is
|
||||
# required and that the macro should error out if no mode with that
|
||||
# support is found. If specified 'optional', then configuration proceeds
|
||||
# regardless, after defining HAVE_CXX${VERSION} if and only if a
|
||||
# supporting mode is found.
|
||||
#
|
||||
# LICENSE
|
||||
#
|
||||
# Copyright (c) 2008 Benjamin Kosnik <bkoz@redhat.com>
|
||||
# Copyright (c) 2012 Zack Weinberg <zackw@panix.com>
|
||||
# Copyright (c) 2013 Roy Stogner <roystgnr@ices.utexas.edu>
|
||||
# Copyright (c) 2014, 2015 Google Inc.; contributed by Alexey Sokolov <sokolov@google.com>
|
||||
# Copyright (c) 2015 Paul Norman <penorman@mac.com>
|
||||
# Copyright (c) 2015 Moritz Klammler <moritz@klammler.eu>
|
||||
# Copyright (c) 2016, 2018 Krzesimir Nowak <qdlacz@gmail.com>
|
||||
#
|
||||
# Copying and distribution of this file, with or without modification, are
|
||||
# permitted in any medium without royalty provided the copyright notice
|
||||
# and this notice are preserved. This file is offered as-is, without any
|
||||
# warranty.
|
||||
|
||||
#serial 10
|
||||
|
||||
dnl This macro is based on the code from the AX_CXX_COMPILE_STDCXX_11 macro
|
||||
dnl (serial version number 13).
|
||||
|
||||
AC_DEFUN([AX_CXX_COMPILE_STDCXX], [dnl
|
||||
m4_if([$1], [11], [ax_cxx_compile_alternatives="11 0x"],
|
||||
[$1], [14], [ax_cxx_compile_alternatives="14 1y"],
|
||||
[$1], [17], [ax_cxx_compile_alternatives="17 1z"],
|
||||
[m4_fatal([invalid first argument `$1' to AX_CXX_COMPILE_STDCXX])])dnl
|
||||
m4_if([$2], [], [],
|
||||
[$2], [ext], [],
|
||||
[$2], [noext], [],
|
||||
[m4_fatal([invalid second argument `$2' to AX_CXX_COMPILE_STDCXX])])dnl
|
||||
m4_if([$3], [], [ax_cxx_compile_cxx$1_required=true],
|
||||
[$3], [mandatory], [ax_cxx_compile_cxx$1_required=true],
|
||||
[$3], [optional], [ax_cxx_compile_cxx$1_required=false],
|
||||
[m4_fatal([invalid third argument `$3' to AX_CXX_COMPILE_STDCXX])])
|
||||
AC_LANG_PUSH([C++])dnl
|
||||
ac_success=no
|
||||
|
||||
m4_if([$2], [noext], [], [dnl
|
||||
if test x$ac_success = xno; then
|
||||
for alternative in ${ax_cxx_compile_alternatives}; do
|
||||
switch="-std=gnu++${alternative}"
|
||||
cachevar=AS_TR_SH([ax_cv_cxx_compile_cxx$1_$switch])
|
||||
AC_CACHE_CHECK(whether $CXX supports C++$1 features with $switch,
|
||||
$cachevar,
|
||||
[ac_save_CXX="$CXX"
|
||||
CXX="$CXX $switch"
|
||||
AC_COMPILE_IFELSE([AC_LANG_SOURCE([_AX_CXX_COMPILE_STDCXX_testbody_$1])],
|
||||
[eval $cachevar=yes],
|
||||
[eval $cachevar=no])
|
||||
CXX="$ac_save_CXX"])
|
||||
if eval test x\$$cachevar = xyes; then
|
||||
CXX="$CXX $switch"
|
||||
if test -n "$CXXCPP" ; then
|
||||
CXXCPP="$CXXCPP $switch"
|
||||
fi
|
||||
ac_success=yes
|
||||
break
|
||||
fi
|
||||
done
|
||||
fi])
|
||||
|
||||
m4_if([$2], [ext], [], [dnl
|
||||
if test x$ac_success = xno; then
|
||||
dnl HP's aCC needs +std=c++11 according to:
|
||||
dnl http://h21007.www2.hp.com/portal/download/files/unprot/aCxx/PDF_Release_Notes/769149-001.pdf
|
||||
dnl Cray's crayCC needs "-h std=c++11"
|
||||
for alternative in ${ax_cxx_compile_alternatives}; do
|
||||
for switch in -std=c++${alternative} +std=c++${alternative} "-h std=c++${alternative}"; do
|
||||
cachevar=AS_TR_SH([ax_cv_cxx_compile_cxx$1_$switch])
|
||||
AC_CACHE_CHECK(whether $CXX supports C++$1 features with $switch,
|
||||
$cachevar,
|
||||
[ac_save_CXX="$CXX"
|
||||
CXX="$CXX $switch"
|
||||
AC_COMPILE_IFELSE([AC_LANG_SOURCE([_AX_CXX_COMPILE_STDCXX_testbody_$1])],
|
||||
[eval $cachevar=yes],
|
||||
[eval $cachevar=no])
|
||||
CXX="$ac_save_CXX"])
|
||||
if eval test x\$$cachevar = xyes; then
|
||||
CXX="$CXX $switch"
|
||||
if test -n "$CXXCPP" ; then
|
||||
CXXCPP="$CXXCPP $switch"
|
||||
fi
|
||||
ac_success=yes
|
||||
break
|
||||
fi
|
||||
done
|
||||
if test x$ac_success = xyes; then
|
||||
break
|
||||
fi
|
||||
done
|
||||
fi])
|
||||
AC_LANG_POP([C++])
|
||||
if test x$ax_cxx_compile_cxx$1_required = xtrue; then
|
||||
if test x$ac_success = xno; then
|
||||
AC_MSG_ERROR([*** A compiler with support for C++$1 language features is required.])
|
||||
fi
|
||||
fi
|
||||
if test x$ac_success = xno; then
|
||||
HAVE_CXX$1=0
|
||||
AC_MSG_NOTICE([No compiler with C++$1 support was found])
|
||||
else
|
||||
HAVE_CXX$1=1
|
||||
AC_DEFINE(HAVE_CXX$1,1,
|
||||
[define if the compiler supports basic C++$1 syntax])
|
||||
fi
|
||||
AC_SUBST(HAVE_CXX$1)
|
||||
])
|
||||
|
||||
|
||||
dnl Test body for checking C++11 support
|
||||
|
||||
m4_define([_AX_CXX_COMPILE_STDCXX_testbody_11],
|
||||
_AX_CXX_COMPILE_STDCXX_testbody_new_in_11
|
||||
)
|
||||
|
||||
|
||||
dnl Test body for checking C++14 support
|
||||
|
||||
m4_define([_AX_CXX_COMPILE_STDCXX_testbody_14],
|
||||
_AX_CXX_COMPILE_STDCXX_testbody_new_in_11
|
||||
_AX_CXX_COMPILE_STDCXX_testbody_new_in_14
|
||||
)
|
||||
|
||||
m4_define([_AX_CXX_COMPILE_STDCXX_testbody_17],
|
||||
_AX_CXX_COMPILE_STDCXX_testbody_new_in_11
|
||||
_AX_CXX_COMPILE_STDCXX_testbody_new_in_14
|
||||
_AX_CXX_COMPILE_STDCXX_testbody_new_in_17
|
||||
)
|
||||
|
||||
dnl Tests for new features in C++11
|
||||
|
||||
m4_define([_AX_CXX_COMPILE_STDCXX_testbody_new_in_11], [[
|
||||
|
||||
// If the compiler admits that it is not ready for C++11, why torture it?
|
||||
// Hopefully, this will speed up the test.
|
||||
|
||||
#ifndef __cplusplus
|
||||
|
||||
#error "This is not a C++ compiler"
|
||||
|
||||
#elif __cplusplus < 201103L
|
||||
|
||||
#error "This is not a C++11 compiler"
|
||||
|
||||
#else
|
||||
|
||||
namespace cxx11
|
||||
{
|
||||
|
||||
namespace test_static_assert
|
||||
{
|
||||
|
||||
template <typename T>
|
||||
struct check
|
||||
{
|
||||
static_assert(sizeof(int) <= sizeof(T), "not big enough");
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
namespace test_final_override
|
||||
{
|
||||
|
||||
struct Base
|
||||
{
|
||||
virtual void f() {}
|
||||
};
|
||||
|
||||
struct Derived : public Base
|
||||
{
|
||||
virtual void f() override {}
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
namespace test_double_right_angle_brackets
|
||||
{
|
||||
|
||||
template < typename T >
|
||||
struct check {};
|
||||
|
||||
typedef check<void> single_type;
|
||||
typedef check<check<void>> double_type;
|
||||
typedef check<check<check<void>>> triple_type;
|
||||
typedef check<check<check<check<void>>>> quadruple_type;
|
||||
|
||||
}
|
||||
|
||||
namespace test_decltype
|
||||
{
|
||||
|
||||
int
|
||||
f()
|
||||
{
|
||||
int a = 1;
|
||||
decltype(a) b = 2;
|
||||
return a + b;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
namespace test_type_deduction
|
||||
{
|
||||
|
||||
template < typename T1, typename T2 >
|
||||
struct is_same
|
||||
{
|
||||
static const bool value = false;
|
||||
};
|
||||
|
||||
template < typename T >
|
||||
struct is_same<T, T>
|
||||
{
|
||||
static const bool value = true;
|
||||
};
|
||||
|
||||
template < typename T1, typename T2 >
|
||||
auto
|
||||
add(T1 a1, T2 a2) -> decltype(a1 + a2)
|
||||
{
|
||||
return a1 + a2;
|
||||
}
|
||||
|
||||
int
|
||||
test(const int c, volatile int v)
|
||||
{
|
||||
static_assert(is_same<int, decltype(0)>::value == true, "");
|
||||
static_assert(is_same<int, decltype(c)>::value == false, "");
|
||||
static_assert(is_same<int, decltype(v)>::value == false, "");
|
||||
auto ac = c;
|
||||
auto av = v;
|
||||
auto sumi = ac + av + 'x';
|
||||
auto sumf = ac + av + 1.0;
|
||||
static_assert(is_same<int, decltype(ac)>::value == true, "");
|
||||
static_assert(is_same<int, decltype(av)>::value == true, "");
|
||||
static_assert(is_same<int, decltype(sumi)>::value == true, "");
|
||||
static_assert(is_same<int, decltype(sumf)>::value == false, "");
|
||||
static_assert(is_same<int, decltype(add(c, v))>::value == true, "");
|
||||
return (sumf > 0.0) ? sumi : add(c, v);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
namespace test_noexcept
|
||||
{
|
||||
|
||||
int f() { return 0; }
|
||||
int g() noexcept { return 0; }
|
||||
|
||||
static_assert(noexcept(f()) == false, "");
|
||||
static_assert(noexcept(g()) == true, "");
|
||||
|
||||
}
|
||||
|
||||
namespace test_constexpr
|
||||
{
|
||||
|
||||
template < typename CharT >
|
||||
unsigned long constexpr
|
||||
strlen_c_r(const CharT *const s, const unsigned long acc) noexcept
|
||||
{
|
||||
return *s ? strlen_c_r(s + 1, acc + 1) : acc;
|
||||
}
|
||||
|
||||
template < typename CharT >
|
||||
unsigned long constexpr
|
||||
strlen_c(const CharT *const s) noexcept
|
||||
{
|
||||
return strlen_c_r(s, 0UL);
|
||||
}
|
||||
|
||||
static_assert(strlen_c("") == 0UL, "");
|
||||
static_assert(strlen_c("1") == 1UL, "");
|
||||
static_assert(strlen_c("example") == 7UL, "");
|
||||
static_assert(strlen_c("another\0example") == 7UL, "");
|
||||
|
||||
}
|
||||
|
||||
namespace test_rvalue_references
|
||||
{
|
||||
|
||||
template < int N >
|
||||
struct answer
|
||||
{
|
||||
static constexpr int value = N;
|
||||
};
|
||||
|
||||
answer<1> f(int&) { return answer<1>(); }
|
||||
answer<2> f(const int&) { return answer<2>(); }
|
||||
answer<3> f(int&&) { return answer<3>(); }
|
||||
|
||||
void
|
||||
test()
|
||||
{
|
||||
int i = 0;
|
||||
const int c = 0;
|
||||
static_assert(decltype(f(i))::value == 1, "");
|
||||
static_assert(decltype(f(c))::value == 2, "");
|
||||
static_assert(decltype(f(0))::value == 3, "");
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
namespace test_uniform_initialization
|
||||
{
|
||||
|
||||
struct test
|
||||
{
|
||||
static const int zero {};
|
||||
static const int one {1};
|
||||
};
|
||||
|
||||
static_assert(test::zero == 0, "");
|
||||
static_assert(test::one == 1, "");
|
||||
|
||||
}
|
||||
|
||||
namespace test_lambdas
|
||||
{
|
||||
|
||||
void
|
||||
test1()
|
||||
{
|
||||
auto lambda1 = [](){};
|
||||
auto lambda2 = lambda1;
|
||||
lambda1();
|
||||
lambda2();
|
||||
}
|
||||
|
||||
int
|
||||
test2()
|
||||
{
|
||||
auto a = [](int i, int j){ return i + j; }(1, 2);
|
||||
auto b = []() -> int { return '0'; }();
|
||||
auto c = [=](){ return a + b; }();
|
||||
auto d = [&](){ return c; }();
|
||||
auto e = [a, &b](int x) mutable {
|
||||
const auto identity = [](int y){ return y; };
|
||||
for (auto i = 0; i < a; ++i)
|
||||
a += b--;
|
||||
return x + identity(a + b);
|
||||
}(0);
|
||||
return a + b + c + d + e;
|
||||
}
|
||||
|
||||
int
|
||||
test3()
|
||||
{
|
||||
const auto nullary = [](){ return 0; };
|
||||
const auto unary = [](int x){ return x; };
|
||||
using nullary_t = decltype(nullary);
|
||||
using unary_t = decltype(unary);
|
||||
const auto higher1st = [](nullary_t f){ return f(); };
|
||||
const auto higher2nd = [unary](nullary_t f1){
|
||||
return [unary, f1](unary_t f2){ return f2(unary(f1())); };
|
||||
};
|
||||
return higher1st(nullary) + higher2nd(nullary)(unary);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
namespace test_variadic_templates
|
||||
{
|
||||
|
||||
template <int...>
|
||||
struct sum;
|
||||
|
||||
template <int N0, int... N1toN>
|
||||
struct sum<N0, N1toN...>
|
||||
{
|
||||
static constexpr auto value = N0 + sum<N1toN...>::value;
|
||||
};
|
||||
|
||||
template <>
|
||||
struct sum<>
|
||||
{
|
||||
static constexpr auto value = 0;
|
||||
};
|
||||
|
||||
static_assert(sum<>::value == 0, "");
|
||||
static_assert(sum<1>::value == 1, "");
|
||||
static_assert(sum<23>::value == 23, "");
|
||||
static_assert(sum<1, 2>::value == 3, "");
|
||||
static_assert(sum<5, 5, 11>::value == 21, "");
|
||||
static_assert(sum<2, 3, 5, 7, 11, 13>::value == 41, "");
|
||||
|
||||
}
|
||||
|
||||
// http://stackoverflow.com/questions/13728184/template-aliases-and-sfinae
|
||||
// Clang 3.1 fails with headers of libstd++ 4.8.3 when using std::function
|
||||
// because of this.
|
||||
namespace test_template_alias_sfinae
|
||||
{
|
||||
|
||||
struct foo {};
|
||||
|
||||
template<typename T>
|
||||
using member = typename T::member_type;
|
||||
|
||||
template<typename T>
|
||||
void func(...) {}
|
||||
|
||||
template<typename T>
|
||||
void func(member<T>*) {}
|
||||
|
||||
void test();
|
||||
|
||||
void test() { func<foo>(0); }
|
||||
|
||||
}
|
||||
|
||||
} // namespace cxx11
|
||||
|
||||
#endif // __cplusplus >= 201103L
|
||||
|
||||
]])
|
||||
|
||||
|
||||
dnl Tests for new features in C++14
|
||||
|
||||
m4_define([_AX_CXX_COMPILE_STDCXX_testbody_new_in_14], [[
|
||||
|
||||
// If the compiler admits that it is not ready for C++14, why torture it?
|
||||
// Hopefully, this will speed up the test.
|
||||
|
||||
#ifndef __cplusplus
|
||||
|
||||
#error "This is not a C++ compiler"
|
||||
|
||||
#elif __cplusplus < 201402L
|
||||
|
||||
#error "This is not a C++14 compiler"
|
||||
|
||||
#else
|
||||
|
||||
namespace cxx14
|
||||
{
|
||||
|
||||
namespace test_polymorphic_lambdas
|
||||
{
|
||||
|
||||
int
|
||||
test()
|
||||
{
|
||||
const auto lambda = [](auto&&... args){
|
||||
const auto istiny = [](auto x){
|
||||
return (sizeof(x) == 1UL) ? 1 : 0;
|
||||
};
|
||||
const int aretiny[] = { istiny(args)... };
|
||||
return aretiny[0];
|
||||
};
|
||||
return lambda(1, 1L, 1.0f, '1');
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
namespace test_binary_literals
|
||||
{
|
||||
|
||||
constexpr auto ivii = 0b0000000000101010;
|
||||
static_assert(ivii == 42, "wrong value");
|
||||
|
||||
}
|
||||
|
||||
namespace test_generalized_constexpr
|
||||
{
|
||||
|
||||
template < typename CharT >
|
||||
constexpr unsigned long
|
||||
strlen_c(const CharT *const s) noexcept
|
||||
{
|
||||
auto length = 0UL;
|
||||
for (auto p = s; *p; ++p)
|
||||
++length;
|
||||
return length;
|
||||
}
|
||||
|
||||
static_assert(strlen_c("") == 0UL, "");
|
||||
static_assert(strlen_c("x") == 1UL, "");
|
||||
static_assert(strlen_c("test") == 4UL, "");
|
||||
static_assert(strlen_c("another\0test") == 7UL, "");
|
||||
|
||||
}
|
||||
|
||||
namespace test_lambda_init_capture
|
||||
{
|
||||
|
||||
int
|
||||
test()
|
||||
{
|
||||
auto x = 0;
|
||||
const auto lambda1 = [a = x](int b){ return a + b; };
|
||||
const auto lambda2 = [a = lambda1(x)](){ return a; };
|
||||
return lambda2();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
namespace test_digit_separators
|
||||
{
|
||||
|
||||
constexpr auto ten_million = 100'000'000;
|
||||
static_assert(ten_million == 100000000, "");
|
||||
|
||||
}
|
||||
|
||||
namespace test_return_type_deduction
|
||||
{
|
||||
|
||||
auto f(int& x) { return x; }
|
||||
decltype(auto) g(int& x) { return x; }
|
||||
|
||||
template < typename T1, typename T2 >
|
||||
struct is_same
|
||||
{
|
||||
static constexpr auto value = false;
|
||||
};
|
||||
|
||||
template < typename T >
|
||||
struct is_same<T, T>
|
||||
{
|
||||
static constexpr auto value = true;
|
||||
};
|
||||
|
||||
int
|
||||
test()
|
||||
{
|
||||
auto x = 0;
|
||||
static_assert(is_same<int, decltype(f(x))>::value, "");
|
||||
static_assert(is_same<int&, decltype(g(x))>::value, "");
|
||||
return x;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
} // namespace cxx14
|
||||
|
||||
#endif // __cplusplus >= 201402L
|
||||
|
||||
]])
|
||||
|
||||
|
||||
dnl Tests for new features in C++17
|
||||
|
||||
m4_define([_AX_CXX_COMPILE_STDCXX_testbody_new_in_17], [[
|
||||
|
||||
// If the compiler admits that it is not ready for C++17, why torture it?
|
||||
// Hopefully, this will speed up the test.
|
||||
|
||||
#ifndef __cplusplus
|
||||
|
||||
#error "This is not a C++ compiler"
|
||||
|
||||
#elif __cplusplus < 201703L
|
||||
|
||||
#error "This is not a C++17 compiler"
|
||||
|
||||
#else
|
||||
|
||||
#include <initializer_list>
|
||||
#include <utility>
|
||||
#include <type_traits>
|
||||
|
||||
namespace cxx17
|
||||
{
|
||||
|
||||
namespace test_constexpr_lambdas
|
||||
{
|
||||
|
||||
constexpr int foo = [](){return 42;}();
|
||||
|
||||
}
|
||||
|
||||
namespace test::nested_namespace::definitions
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
namespace test_fold_expression
|
||||
{
|
||||
|
||||
template<typename... Args>
|
||||
int multiply(Args... args)
|
||||
{
|
||||
return (args * ... * 1);
|
||||
}
|
||||
|
||||
template<typename... Args>
|
||||
bool all(Args... args)
|
||||
{
|
||||
return (args && ...);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
namespace test_extended_static_assert
|
||||
{
|
||||
|
||||
static_assert (true);
|
||||
|
||||
}
|
||||
|
||||
namespace test_auto_brace_init_list
|
||||
{
|
||||
|
||||
auto foo = {5};
|
||||
auto bar {5};
|
||||
|
||||
static_assert(std::is_same<std::initializer_list<int>, decltype(foo)>::value);
|
||||
static_assert(std::is_same<int, decltype(bar)>::value);
|
||||
}
|
||||
|
||||
namespace test_typename_in_template_template_parameter
|
||||
{
|
||||
|
||||
template<template<typename> typename X> struct D;
|
||||
|
||||
}
|
||||
|
||||
namespace test_fallthrough_nodiscard_maybe_unused_attributes
|
||||
{
|
||||
|
||||
int f1()
|
||||
{
|
||||
return 42;
|
||||
}
|
||||
|
||||
[[nodiscard]] int f2()
|
||||
{
|
||||
[[maybe_unused]] auto unused = f1();
|
||||
|
||||
switch (f1())
|
||||
{
|
||||
case 17:
|
||||
f1();
|
||||
[[fallthrough]];
|
||||
case 42:
|
||||
f1();
|
||||
}
|
||||
return f1();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
namespace test_extended_aggregate_initialization
|
||||
{
|
||||
|
||||
struct base1
|
||||
{
|
||||
int b1, b2 = 42;
|
||||
};
|
||||
|
||||
struct base2
|
||||
{
|
||||
base2() {
|
||||
b3 = 42;
|
||||
}
|
||||
int b3;
|
||||
};
|
||||
|
||||
struct derived : base1, base2
|
||||
{
|
||||
int d;
|
||||
};
|
||||
|
||||
derived d1 {{1, 2}, {}, 4}; // full initialization
|
||||
derived d2 {{}, {}, 4}; // value-initialized bases
|
||||
|
||||
}
|
||||
|
||||
namespace test_general_range_based_for_loop
|
||||
{
|
||||
|
||||
struct iter
|
||||
{
|
||||
int i;
|
||||
|
||||
int& operator* ()
|
||||
{
|
||||
return i;
|
||||
}
|
||||
|
||||
const int& operator* () const
|
||||
{
|
||||
return i;
|
||||
}
|
||||
|
||||
iter& operator++()
|
||||
{
|
||||
++i;
|
||||
return *this;
|
||||
}
|
||||
};
|
||||
|
||||
struct sentinel
|
||||
{
|
||||
int i;
|
||||
};
|
||||
|
||||
bool operator== (const iter& i, const sentinel& s)
|
||||
{
|
||||
return i.i == s.i;
|
||||
}
|
||||
|
||||
bool operator!= (const iter& i, const sentinel& s)
|
||||
{
|
||||
return !(i == s);
|
||||
}
|
||||
|
||||
struct range
|
||||
{
|
||||
iter begin() const
|
||||
{
|
||||
return {0};
|
||||
}
|
||||
|
||||
sentinel end() const
|
||||
{
|
||||
return {5};
|
||||
}
|
||||
};
|
||||
|
||||
void f()
|
||||
{
|
||||
range r {};
|
||||
|
||||
for (auto i : r)
|
||||
{
|
||||
[[maybe_unused]] auto v = i;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
namespace test_lambda_capture_asterisk_this_by_value
|
||||
{
|
||||
|
||||
struct t
|
||||
{
|
||||
int i;
|
||||
int foo()
|
||||
{
|
||||
return [*this]()
|
||||
{
|
||||
return i;
|
||||
}();
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
namespace test_enum_class_construction
|
||||
{
|
||||
|
||||
enum class byte : unsigned char
|
||||
{};
|
||||
|
||||
byte foo {42};
|
||||
|
||||
}
|
||||
|
||||
namespace test_constexpr_if
|
||||
{
|
||||
|
||||
template <bool cond>
|
||||
int f ()
|
||||
{
|
||||
if constexpr(cond)
|
||||
{
|
||||
return 13;
|
||||
}
|
||||
else
|
||||
{
|
||||
return 42;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
namespace test_selection_statement_with_initializer
|
||||
{
|
||||
|
||||
int f()
|
||||
{
|
||||
return 13;
|
||||
}
|
||||
|
||||
int f2()
|
||||
{
|
||||
if (auto i = f(); i > 0)
|
||||
{
|
||||
return 3;
|
||||
}
|
||||
|
||||
switch (auto i = f(); i + 4)
|
||||
{
|
||||
case 17:
|
||||
return 2;
|
||||
|
||||
default:
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
namespace test_template_argument_deduction_for_class_templates
|
||||
{
|
||||
|
||||
template <typename T1, typename T2>
|
||||
struct pair
|
||||
{
|
||||
pair (T1 p1, T2 p2)
|
||||
: m1 {p1},
|
||||
m2 {p2}
|
||||
{}
|
||||
|
||||
T1 m1;
|
||||
T2 m2;
|
||||
};
|
||||
|
||||
void f()
|
||||
{
|
||||
[[maybe_unused]] auto p = pair{13, 42u};
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
namespace test_non_type_auto_template_parameters
|
||||
{
|
||||
|
||||
template <auto n>
|
||||
struct B
|
||||
{};
|
||||
|
||||
B<5> b1;
|
||||
B<'a'> b2;
|
||||
|
||||
}
|
||||
|
||||
namespace test_structured_bindings
|
||||
{
|
||||
|
||||
int arr[2] = { 1, 2 };
|
||||
std::pair<int, int> pr = { 1, 2 };
|
||||
|
||||
auto f1() -> int(&)[2]
|
||||
{
|
||||
return arr;
|
||||
}
|
||||
|
||||
auto f2() -> std::pair<int, int>&
|
||||
{
|
||||
return pr;
|
||||
}
|
||||
|
||||
struct S
|
||||
{
|
||||
int x1 : 2;
|
||||
volatile double y1;
|
||||
};
|
||||
|
||||
S f3()
|
||||
{
|
||||
return {};
|
||||
}
|
||||
|
||||
auto [ x1, y1 ] = f1();
|
||||
auto& [ xr1, yr1 ] = f1();
|
||||
auto [ x2, y2 ] = f2();
|
||||
auto& [ xr2, yr2 ] = f2();
|
||||
const auto [ x3, y3 ] = f3();
|
||||
|
||||
}
|
||||
|
||||
namespace test_exception_spec_type_system
|
||||
{
|
||||
|
||||
struct Good {};
|
||||
struct Bad {};
|
||||
|
||||
void g1() noexcept;
|
||||
void g2();
|
||||
|
||||
template<typename T>
|
||||
Bad
|
||||
f(T*, T*);
|
||||
|
||||
template<typename T1, typename T2>
|
||||
Good
|
||||
f(T1*, T2*);
|
||||
|
||||
static_assert (std::is_same_v<Good, decltype(f(g1, g2))>);
|
||||
|
||||
}
|
||||
|
||||
namespace test_inline_variables
|
||||
{
|
||||
|
||||
template<class T> void f(T)
|
||||
{}
|
||||
|
||||
template<class T> inline T g(T)
|
||||
{
|
||||
return T{};
|
||||
}
|
||||
|
||||
template<> inline void f<>(int)
|
||||
{}
|
||||
|
||||
template<> int g<>(int)
|
||||
{
|
||||
return 5;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
} // namespace cxx17
|
||||
|
||||
#endif // __cplusplus < 201703L
|
||||
|
||||
]])
|
99
trunk/3rdparty/gperftools-2-fit/m4/ax_generate_changelog.m4
vendored
Normal file
|
@ -0,0 +1,99 @@
|
|||
# ===========================================================================
|
||||
# http://www.gnu.org/software/autoconf-archive/ax_generate_changelog.html
|
||||
# ===========================================================================
|
||||
#
|
||||
# SYNOPSIS
|
||||
#
|
||||
# AX_GENERATE_CHANGELOG()
|
||||
#
|
||||
# DESCRIPTION
|
||||
#
|
||||
# Builds a rule for generating a ChangeLog file from version control
|
||||
# system commit messages. Currently, the only supported VCS is git, but
|
||||
# support for others could be added in future.
|
||||
#
|
||||
# Defines GENERATE_CHANGELOG_RULES which should be substituted in your
|
||||
# Makefile.
|
||||
#
|
||||
# Usage example:
|
||||
#
|
||||
# configure.ac:
|
||||
#
|
||||
# AX_GENERATE_CHANGELOG
|
||||
#
|
||||
# Makefile.am:
|
||||
#
|
||||
# @GENERATE_CHANGELOG_RULES@
|
||||
# CHANGELOG_START = 0.2.3^
|
||||
# dist-hook: dist-ChangeLog
|
||||
#
|
||||
# ChangeLog (stub committed to VCS):
|
||||
#
|
||||
# The ChangeLog is auto-generated when releasing.
|
||||
# If you are seeing this, use 'git log' for a detailed list of changes.
|
||||
#
|
||||
# This results in a "dist-ChangeLog" rule being added to the Makefile.
|
||||
# When run, "dist-ChangeLog" will generate a ChangeLog in the
|
||||
# $(top_distdir), using $(CHANGELOG_GIT_FLAGS) to format the output from
|
||||
# "git log" being run in $(CHANGELOG_GIT_DIR).
|
||||
#
|
||||
# Unless Automake is initialised with the 'foreign' option, a dummy
|
||||
# ChangeLog file must be committed to VCS in $(top_srcdir), containing the
|
||||
# text above (for example). It will be substituted by the automatically
|
||||
# generated ChangeLog during "make dist".
|
||||
#
|
||||
# LICENSE
|
||||
#
|
||||
# Copyright (c) 2015 David King <amigadave@amigadave.com>
|
||||
# Copyright (c) 2015 Philip Withnall <philip.withnall@collabora.co.uk>
|
||||
#
|
||||
# Copying and distribution of this file, with or without modification, are
|
||||
# permitted in any medium without royalty provided the copyright notice
|
||||
# and this notice are preserved. This file is offered as-is, without any
|
||||
# warranty.
|
||||
|
||||
#serial 1
|
||||
|
||||
AC_DEFUN([AX_GENERATE_CHANGELOG],[
|
||||
# Find git, defaulting to the 'missing' script so the user gets a nice
|
||||
# message if git is missing, rather than a plain 'command not found'.
|
||||
AC_PATH_PROG([GIT],[git],[${am_missing_run}git])
|
||||
AC_SUBST([GIT])
|
||||
|
||||
# Build the ChangeLog rules.
|
||||
m4_pattern_allow([AM_V_GEN])
|
||||
GENERATE_CHANGELOG_RULES='
|
||||
# Generate ChangeLog
|
||||
#
|
||||
# Optional:
|
||||
# - CHANGELOG_START: git commit ID or tag name to output changelogs from
|
||||
# (exclusive). (Default: include all commits)
|
||||
# - CHANGELOG_GIT_FLAGS: General flags to pass to git-log when generating the
|
||||
# ChangeLog. (Default: various)
|
||||
# - CHANGELOG_GIT_DIR: .git directory to use. (Default: $(top_srcdir)/.git)
|
||||
|
||||
# git-specific
|
||||
CHANGELOG_GIT_FLAGS ?= --stat -M -C --name-status --no-color
|
||||
CHANGELOG_GIT_DIR ?= $(top_srcdir)/.git
|
||||
|
||||
ifeq ($(CHANGELOG_START),)
|
||||
CHANGELOG_GIT_RANGE =
|
||||
else
|
||||
CHANGELOG_GIT_RANGE = $(CHANGELOG_START)..
|
||||
endif
|
||||
|
||||
# Generate a ChangeLog in $(top_distdir)
|
||||
dist-ChangeLog:
|
||||
$(AM_V_GEN)if $(GIT) \
|
||||
--git-dir=$(CHANGELOG_GIT_DIR) --work-tree=$(top_srcdir) log \
|
||||
$(CHANGELOG_GIT_FLAGS) $(CHANGELOG_GIT_RANGE) \
|
||||
| fmt --split-only >.ChangeLog.tmp; \
|
||||
then mv -f .ChangeLog.tmp "$(top_distdir)/ChangeLog"; \
|
||||
else rm -f .ChangeLog.tmp; exit 1; fi
|
||||
|
||||
.PHONY: dist-ChangeLog
|
||||
'
|
||||
|
||||
AC_SUBST([GENERATE_CHANGELOG_RULES])
|
||||
m4_ifdef([_AM_SUBST_NOTMAKE], [_AM_SUBST_NOTMAKE([GENERATE_CHANGELOG_RULES])])
|
||||
])
|
8
trunk/3rdparty/gperftools-2-fit/m4/install_prefix.m4
vendored
Normal file
|
@ -0,0 +1,8 @@
|
|||
AC_DEFUN([AC_INSTALL_PREFIX],
|
||||
[ac_cv_install_prefix="$prefix";
|
||||
if test x"$ac_cv_install_prefix" = x"NONE" ; then
|
||||
ac_cv_install_prefix="$ac_default_prefix";
|
||||
fi
|
||||
AC_DEFINE_UNQUOTED(INSTALL_PREFIX, "$ac_cv_install_prefix",
|
||||
[prefix where we look for installed files])
|
||||
])
|
8394
trunk/3rdparty/gperftools-2-fit/m4/libtool.m4
vendored
Normal file
437
trunk/3rdparty/gperftools-2-fit/m4/ltoptions.m4
vendored
Normal file
|
@ -0,0 +1,437 @@
|
|||
# Helper functions for option handling. -*- Autoconf -*-
|
||||
#
|
||||
# Copyright (C) 2004-2005, 2007-2009, 2011-2015 Free Software
|
||||
# Foundation, Inc.
|
||||
# Written by Gary V. Vaughan, 2004
|
||||
#
|
||||
# This file is free software; the Free Software Foundation gives
|
||||
# unlimited permission to copy and/or distribute it, with or without
|
||||
# modifications, as long as this notice is preserved.
|
||||
|
||||
# serial 8 ltoptions.m4
|
||||
|
||||
# This is to help aclocal find these macros, as it can't see m4_define.
|
||||
AC_DEFUN([LTOPTIONS_VERSION], [m4_if([1])])
|
||||
|
||||
|
||||
# _LT_MANGLE_OPTION(MACRO-NAME, OPTION-NAME)
|
||||
# ------------------------------------------
|
||||
m4_define([_LT_MANGLE_OPTION],
|
||||
[[_LT_OPTION_]m4_bpatsubst($1__$2, [[^a-zA-Z0-9_]], [_])])
|
||||
|
||||
|
||||
# _LT_SET_OPTION(MACRO-NAME, OPTION-NAME)
|
||||
# ---------------------------------------
|
||||
# Set option OPTION-NAME for macro MACRO-NAME, and if there is a
|
||||
# matching handler defined, dispatch to it. Other OPTION-NAMEs are
|
||||
# saved as a flag.
|
||||
m4_define([_LT_SET_OPTION],
|
||||
[m4_define(_LT_MANGLE_OPTION([$1], [$2]))dnl
|
||||
m4_ifdef(_LT_MANGLE_DEFUN([$1], [$2]),
|
||||
_LT_MANGLE_DEFUN([$1], [$2]),
|
||||
[m4_warning([Unknown $1 option '$2'])])[]dnl
|
||||
])
|
||||
|
||||
|
||||
# _LT_IF_OPTION(MACRO-NAME, OPTION-NAME, IF-SET, [IF-NOT-SET])
|
||||
# ------------------------------------------------------------
|
||||
# Execute IF-SET if OPTION is set, IF-NOT-SET otherwise.
|
||||
m4_define([_LT_IF_OPTION],
|
||||
[m4_ifdef(_LT_MANGLE_OPTION([$1], [$2]), [$3], [$4])])
|
||||
|
||||
|
||||
# _LT_UNLESS_OPTIONS(MACRO-NAME, OPTION-LIST, IF-NOT-SET)
|
||||
# -------------------------------------------------------
|
||||
# Execute IF-NOT-SET unless all options in OPTION-LIST for MACRO-NAME
|
||||
# are set.
|
||||
m4_define([_LT_UNLESS_OPTIONS],
|
||||
[m4_foreach([_LT_Option], m4_split(m4_normalize([$2])),
|
||||
[m4_ifdef(_LT_MANGLE_OPTION([$1], _LT_Option),
|
||||
[m4_define([$0_found])])])[]dnl
|
||||
m4_ifdef([$0_found], [m4_undefine([$0_found])], [$3
|
||||
])[]dnl
|
||||
])
|
||||
|
||||
|
||||
# _LT_SET_OPTIONS(MACRO-NAME, OPTION-LIST)
|
||||
# ----------------------------------------
|
||||
# OPTION-LIST is a space-separated list of Libtool options associated
|
||||
# with MACRO-NAME. If any OPTION has a matching handler declared with
|
||||
# LT_OPTION_DEFINE, dispatch to that macro; otherwise complain about
|
||||
# the unknown option and exit.
|
||||
m4_defun([_LT_SET_OPTIONS],
|
||||
[# Set options
|
||||
m4_foreach([_LT_Option], m4_split(m4_normalize([$2])),
|
||||
[_LT_SET_OPTION([$1], _LT_Option)])
|
||||
|
||||
m4_if([$1],[LT_INIT],[
|
||||
dnl
|
||||
dnl Simply set some default values (i.e off) if boolean options were not
|
||||
dnl specified:
|
||||
_LT_UNLESS_OPTIONS([LT_INIT], [dlopen], [enable_dlopen=no
|
||||
])
|
||||
_LT_UNLESS_OPTIONS([LT_INIT], [win32-dll], [enable_win32_dll=no
|
||||
])
|
||||
dnl
|
||||
dnl If no reference was made to various pairs of opposing options, then
|
||||
dnl we run the default mode handler for the pair. For example, if neither
|
||||
dnl 'shared' nor 'disable-shared' was passed, we enable building of shared
|
||||
dnl archives by default:
|
||||
_LT_UNLESS_OPTIONS([LT_INIT], [shared disable-shared], [_LT_ENABLE_SHARED])
|
||||
_LT_UNLESS_OPTIONS([LT_INIT], [static disable-static], [_LT_ENABLE_STATIC])
|
||||
_LT_UNLESS_OPTIONS([LT_INIT], [pic-only no-pic], [_LT_WITH_PIC])
|
||||
_LT_UNLESS_OPTIONS([LT_INIT], [fast-install disable-fast-install],
|
||||
[_LT_ENABLE_FAST_INSTALL])
|
||||
_LT_UNLESS_OPTIONS([LT_INIT], [aix-soname=aix aix-soname=both aix-soname=svr4],
|
||||
[_LT_WITH_AIX_SONAME([aix])])
|
||||
])
|
||||
])# _LT_SET_OPTIONS
|
||||
|
||||
|
||||
## --------------------------------- ##
|
||||
## Macros to handle LT_INIT options. ##
|
||||
## --------------------------------- ##
|
||||
|
||||
# _LT_MANGLE_DEFUN(MACRO-NAME, OPTION-NAME)
|
||||
# -----------------------------------------
|
||||
m4_define([_LT_MANGLE_DEFUN],
|
||||
[[_LT_OPTION_DEFUN_]m4_bpatsubst(m4_toupper([$1__$2]), [[^A-Z0-9_]], [_])])
|
||||
|
||||
|
||||
# LT_OPTION_DEFINE(MACRO-NAME, OPTION-NAME, CODE)
|
||||
# -----------------------------------------------
|
||||
m4_define([LT_OPTION_DEFINE],
|
||||
[m4_define(_LT_MANGLE_DEFUN([$1], [$2]), [$3])[]dnl
|
||||
])# LT_OPTION_DEFINE
|
||||
|
||||
|
||||
# dlopen
|
||||
# ------
|
||||
LT_OPTION_DEFINE([LT_INIT], [dlopen], [enable_dlopen=yes
|
||||
])
|
||||
|
||||
AU_DEFUN([AC_LIBTOOL_DLOPEN],
|
||||
[_LT_SET_OPTION([LT_INIT], [dlopen])
|
||||
AC_DIAGNOSE([obsolete],
|
||||
[$0: Remove this warning and the call to _LT_SET_OPTION when you
|
||||
put the 'dlopen' option into LT_INIT's first parameter.])
|
||||
])
|
||||
|
||||
dnl aclocal-1.4 backwards compatibility:
|
||||
dnl AC_DEFUN([AC_LIBTOOL_DLOPEN], [])
|
||||
|
||||
|
||||
# win32-dll
|
||||
# ---------
|
||||
# Declare package support for building win32 dll's.
|
||||
LT_OPTION_DEFINE([LT_INIT], [win32-dll],
|
||||
[enable_win32_dll=yes
|
||||
|
||||
case $host in
|
||||
*-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-cegcc*)
|
||||
AC_CHECK_TOOL(AS, as, false)
|
||||
AC_CHECK_TOOL(DLLTOOL, dlltool, false)
|
||||
AC_CHECK_TOOL(OBJDUMP, objdump, false)
|
||||
;;
|
||||
esac
|
||||
|
||||
test -z "$AS" && AS=as
|
||||
_LT_DECL([], [AS], [1], [Assembler program])dnl
|
||||
|
||||
test -z "$DLLTOOL" && DLLTOOL=dlltool
|
||||
_LT_DECL([], [DLLTOOL], [1], [DLL creation program])dnl
|
||||
|
||||
test -z "$OBJDUMP" && OBJDUMP=objdump
|
||||
_LT_DECL([], [OBJDUMP], [1], [Object dumper program])dnl
|
||||
])# win32-dll
|
||||
|
||||
AU_DEFUN([AC_LIBTOOL_WIN32_DLL],
|
||||
[AC_REQUIRE([AC_CANONICAL_HOST])dnl
|
||||
_LT_SET_OPTION([LT_INIT], [win32-dll])
|
||||
AC_DIAGNOSE([obsolete],
|
||||
[$0: Remove this warning and the call to _LT_SET_OPTION when you
|
||||
put the 'win32-dll' option into LT_INIT's first parameter.])
|
||||
])
|
||||
|
||||
dnl aclocal-1.4 backwards compatibility:
|
||||
dnl AC_DEFUN([AC_LIBTOOL_WIN32_DLL], [])
|
||||
|
||||
|
||||
# _LT_ENABLE_SHARED([DEFAULT])
|
||||
# ----------------------------
|
||||
# implement the --enable-shared flag, and supports the 'shared' and
|
||||
# 'disable-shared' LT_INIT options.
|
||||
# DEFAULT is either 'yes' or 'no'. If omitted, it defaults to 'yes'.
|
||||
m4_define([_LT_ENABLE_SHARED],
|
||||
[m4_define([_LT_ENABLE_SHARED_DEFAULT], [m4_if($1, no, no, yes)])dnl
|
||||
AC_ARG_ENABLE([shared],
|
||||
[AS_HELP_STRING([--enable-shared@<:@=PKGS@:>@],
|
||||
[build shared libraries @<:@default=]_LT_ENABLE_SHARED_DEFAULT[@:>@])],
|
||||
[p=${PACKAGE-default}
|
||||
case $enableval in
|
||||
yes) enable_shared=yes ;;
|
||||
no) enable_shared=no ;;
|
||||
*)
|
||||
enable_shared=no
|
||||
# Look at the argument we got. We use all the common list separators.
|
||||
lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR,
|
||||
for pkg in $enableval; do
|
||||
IFS=$lt_save_ifs
|
||||
if test "X$pkg" = "X$p"; then
|
||||
enable_shared=yes
|
||||
fi
|
||||
done
|
||||
IFS=$lt_save_ifs
|
||||
;;
|
||||
esac],
|
||||
[enable_shared=]_LT_ENABLE_SHARED_DEFAULT)
|
||||
|
||||
_LT_DECL([build_libtool_libs], [enable_shared], [0],
|
||||
[Whether or not to build shared libraries])
|
||||
])# _LT_ENABLE_SHARED
|
||||
|
||||
LT_OPTION_DEFINE([LT_INIT], [shared], [_LT_ENABLE_SHARED([yes])])
|
||||
LT_OPTION_DEFINE([LT_INIT], [disable-shared], [_LT_ENABLE_SHARED([no])])
|
||||
|
||||
# Old names:
|
||||
AC_DEFUN([AC_ENABLE_SHARED],
|
||||
[_LT_SET_OPTION([LT_INIT], m4_if([$1], [no], [disable-])[shared])
|
||||
])
|
||||
|
||||
AC_DEFUN([AC_DISABLE_SHARED],
|
||||
[_LT_SET_OPTION([LT_INIT], [disable-shared])
|
||||
])
|
||||
|
||||
AU_DEFUN([AM_ENABLE_SHARED], [AC_ENABLE_SHARED($@)])
|
||||
AU_DEFUN([AM_DISABLE_SHARED], [AC_DISABLE_SHARED($@)])
|
||||
|
||||
dnl aclocal-1.4 backwards compatibility:
|
||||
dnl AC_DEFUN([AM_ENABLE_SHARED], [])
|
||||
dnl AC_DEFUN([AM_DISABLE_SHARED], [])
|
||||
|
||||
|
||||
|
||||
# _LT_ENABLE_STATIC([DEFAULT])
|
||||
# ----------------------------
|
||||
# implement the --enable-static flag, and support the 'static' and
|
||||
# 'disable-static' LT_INIT options.
|
||||
# DEFAULT is either 'yes' or 'no'. If omitted, it defaults to 'yes'.
|
||||
m4_define([_LT_ENABLE_STATIC],
|
||||
[m4_define([_LT_ENABLE_STATIC_DEFAULT], [m4_if($1, no, no, yes)])dnl
|
||||
AC_ARG_ENABLE([static],
|
||||
[AS_HELP_STRING([--enable-static@<:@=PKGS@:>@],
|
||||
[build static libraries @<:@default=]_LT_ENABLE_STATIC_DEFAULT[@:>@])],
|
||||
[p=${PACKAGE-default}
|
||||
case $enableval in
|
||||
yes) enable_static=yes ;;
|
||||
no) enable_static=no ;;
|
||||
*)
|
||||
enable_static=no
|
||||
# Look at the argument we got. We use all the common list separators.
|
||||
lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR,
|
||||
for pkg in $enableval; do
|
||||
IFS=$lt_save_ifs
|
||||
if test "X$pkg" = "X$p"; then
|
||||
enable_static=yes
|
||||
fi
|
||||
done
|
||||
IFS=$lt_save_ifs
|
||||
;;
|
||||
esac],
|
||||
[enable_static=]_LT_ENABLE_STATIC_DEFAULT)
|
||||
|
||||
_LT_DECL([build_old_libs], [enable_static], [0],
|
||||
[Whether or not to build static libraries])
|
||||
])# _LT_ENABLE_STATIC
|
||||
|
||||
LT_OPTION_DEFINE([LT_INIT], [static], [_LT_ENABLE_STATIC([yes])])
|
||||
LT_OPTION_DEFINE([LT_INIT], [disable-static], [_LT_ENABLE_STATIC([no])])
|
||||
|
||||
# Old names:
|
||||
AC_DEFUN([AC_ENABLE_STATIC],
|
||||
[_LT_SET_OPTION([LT_INIT], m4_if([$1], [no], [disable-])[static])
|
||||
])
|
||||
|
||||
AC_DEFUN([AC_DISABLE_STATIC],
|
||||
[_LT_SET_OPTION([LT_INIT], [disable-static])
|
||||
])
|
||||
|
||||
AU_DEFUN([AM_ENABLE_STATIC], [AC_ENABLE_STATIC($@)])
|
||||
AU_DEFUN([AM_DISABLE_STATIC], [AC_DISABLE_STATIC($@)])
|
||||
|
||||
dnl aclocal-1.4 backwards compatibility:
|
||||
dnl AC_DEFUN([AM_ENABLE_STATIC], [])
|
||||
dnl AC_DEFUN([AM_DISABLE_STATIC], [])
|
||||
|
||||
|
||||
|
||||
# _LT_ENABLE_FAST_INSTALL([DEFAULT])
|
||||
# ----------------------------------
|
||||
# implement the --enable-fast-install flag, and support the 'fast-install'
|
||||
# and 'disable-fast-install' LT_INIT options.
|
||||
# DEFAULT is either 'yes' or 'no'. If omitted, it defaults to 'yes'.
|
||||
m4_define([_LT_ENABLE_FAST_INSTALL],
|
||||
[m4_define([_LT_ENABLE_FAST_INSTALL_DEFAULT], [m4_if($1, no, no, yes)])dnl
|
||||
AC_ARG_ENABLE([fast-install],
|
||||
[AS_HELP_STRING([--enable-fast-install@<:@=PKGS@:>@],
|
||||
[optimize for fast installation @<:@default=]_LT_ENABLE_FAST_INSTALL_DEFAULT[@:>@])],
|
||||
[p=${PACKAGE-default}
|
||||
case $enableval in
|
||||
yes) enable_fast_install=yes ;;
|
||||
no) enable_fast_install=no ;;
|
||||
*)
|
||||
enable_fast_install=no
|
||||
# Look at the argument we got. We use all the common list separators.
|
||||
lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR,
|
||||
for pkg in $enableval; do
|
||||
IFS=$lt_save_ifs
|
||||
if test "X$pkg" = "X$p"; then
|
||||
enable_fast_install=yes
|
||||
fi
|
||||
done
|
||||
IFS=$lt_save_ifs
|
||||
;;
|
||||
esac],
|
||||
[enable_fast_install=]_LT_ENABLE_FAST_INSTALL_DEFAULT)
|
||||
|
||||
_LT_DECL([fast_install], [enable_fast_install], [0],
|
||||
[Whether or not to optimize for fast installation])dnl
|
||||
])# _LT_ENABLE_FAST_INSTALL
|
||||
|
||||
LT_OPTION_DEFINE([LT_INIT], [fast-install], [_LT_ENABLE_FAST_INSTALL([yes])])
|
||||
LT_OPTION_DEFINE([LT_INIT], [disable-fast-install], [_LT_ENABLE_FAST_INSTALL([no])])
|
||||
|
||||
# Old names:
|
||||
AU_DEFUN([AC_ENABLE_FAST_INSTALL],
|
||||
[_LT_SET_OPTION([LT_INIT], m4_if([$1], [no], [disable-])[fast-install])
|
||||
AC_DIAGNOSE([obsolete],
|
||||
[$0: Remove this warning and the call to _LT_SET_OPTION when you put
|
||||
the 'fast-install' option into LT_INIT's first parameter.])
|
||||
])
|
||||
|
||||
AU_DEFUN([AC_DISABLE_FAST_INSTALL],
|
||||
[_LT_SET_OPTION([LT_INIT], [disable-fast-install])
|
||||
AC_DIAGNOSE([obsolete],
|
||||
[$0: Remove this warning and the call to _LT_SET_OPTION when you put
|
||||
the 'disable-fast-install' option into LT_INIT's first parameter.])
|
||||
])
|
||||
|
||||
dnl aclocal-1.4 backwards compatibility:
|
||||
dnl AC_DEFUN([AC_ENABLE_FAST_INSTALL], [])
|
||||
dnl AC_DEFUN([AM_DISABLE_FAST_INSTALL], [])
|
||||
|
||||
|
||||
# _LT_WITH_AIX_SONAME([DEFAULT])
|
||||
# ----------------------------------
|
||||
# implement the --with-aix-soname flag, and support the `aix-soname=aix'
|
||||
# and `aix-soname=both' and `aix-soname=svr4' LT_INIT options. DEFAULT
|
||||
# is either `aix', `both' or `svr4'. If omitted, it defaults to `aix'.
|
||||
m4_define([_LT_WITH_AIX_SONAME],
|
||||
[m4_define([_LT_WITH_AIX_SONAME_DEFAULT], [m4_if($1, svr4, svr4, m4_if($1, both, both, aix))])dnl
|
||||
shared_archive_member_spec=
|
||||
case $host,$enable_shared in
|
||||
power*-*-aix[[5-9]]*,yes)
|
||||
AC_MSG_CHECKING([which variant of shared library versioning to provide])
|
||||
AC_ARG_WITH([aix-soname],
|
||||
[AS_HELP_STRING([--with-aix-soname=aix|svr4|both],
|
||||
[shared library versioning (aka "SONAME") variant to provide on AIX, @<:@default=]_LT_WITH_AIX_SONAME_DEFAULT[@:>@.])],
|
||||
[case $withval in
|
||||
aix|svr4|both)
|
||||
;;
|
||||
*)
|
||||
AC_MSG_ERROR([Unknown argument to --with-aix-soname])
|
||||
;;
|
||||
esac
|
||||
lt_cv_with_aix_soname=$with_aix_soname],
|
||||
[AC_CACHE_VAL([lt_cv_with_aix_soname],
|
||||
[lt_cv_with_aix_soname=]_LT_WITH_AIX_SONAME_DEFAULT)
|
||||
with_aix_soname=$lt_cv_with_aix_soname])
|
||||
AC_MSG_RESULT([$with_aix_soname])
|
||||
if test aix != "$with_aix_soname"; then
|
||||
# For the AIX way of multilib, we name the shared archive member
|
||||
# based on the bitwidth used, traditionally 'shr.o' or 'shr_64.o',
|
||||
# and 'shr.imp' or 'shr_64.imp', respectively, for the Import File.
|
||||
# Even when GNU compilers ignore OBJECT_MODE but need '-maix64' flag,
|
||||
# the AIX toolchain works better with OBJECT_MODE set (default 32).
|
||||
if test 64 = "${OBJECT_MODE-32}"; then
|
||||
shared_archive_member_spec=shr_64
|
||||
else
|
||||
shared_archive_member_spec=shr
|
||||
fi
|
||||
fi
|
||||
;;
|
||||
*)
|
||||
with_aix_soname=aix
|
||||
;;
|
||||
esac
|
||||
|
||||
_LT_DECL([], [shared_archive_member_spec], [0],
|
||||
[Shared archive member basename, for filename based shared library versioning on AIX])dnl
|
||||
])# _LT_WITH_AIX_SONAME
|
||||
|
||||
LT_OPTION_DEFINE([LT_INIT], [aix-soname=aix], [_LT_WITH_AIX_SONAME([aix])])
|
||||
LT_OPTION_DEFINE([LT_INIT], [aix-soname=both], [_LT_WITH_AIX_SONAME([both])])
|
||||
LT_OPTION_DEFINE([LT_INIT], [aix-soname=svr4], [_LT_WITH_AIX_SONAME([svr4])])
|
||||
|
||||
|
||||
# _LT_WITH_PIC([MODE])
|
||||
# --------------------
|
||||
# implement the --with-pic flag, and support the 'pic-only' and 'no-pic'
|
||||
# LT_INIT options.
|
||||
# MODE is either 'yes' or 'no'. If omitted, it defaults to 'both'.
|
||||
m4_define([_LT_WITH_PIC],
|
||||
[AC_ARG_WITH([pic],
|
||||
[AS_HELP_STRING([--with-pic@<:@=PKGS@:>@],
|
||||
[try to use only PIC/non-PIC objects @<:@default=use both@:>@])],
|
||||
[lt_p=${PACKAGE-default}
|
||||
case $withval in
|
||||
yes|no) pic_mode=$withval ;;
|
||||
*)
|
||||
pic_mode=default
|
||||
# Look at the argument we got. We use all the common list separators.
|
||||
lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR,
|
||||
for lt_pkg in $withval; do
|
||||
IFS=$lt_save_ifs
|
||||
if test "X$lt_pkg" = "X$lt_p"; then
|
||||
pic_mode=yes
|
||||
fi
|
||||
done
|
||||
IFS=$lt_save_ifs
|
||||
;;
|
||||
esac],
|
||||
[pic_mode=m4_default([$1], [default])])
|
||||
|
||||
_LT_DECL([], [pic_mode], [0], [What type of objects to build])dnl
|
||||
])# _LT_WITH_PIC
|
||||
|
||||
LT_OPTION_DEFINE([LT_INIT], [pic-only], [_LT_WITH_PIC([yes])])
|
||||
LT_OPTION_DEFINE([LT_INIT], [no-pic], [_LT_WITH_PIC([no])])
|
||||
|
||||
# Old name:
|
||||
AU_DEFUN([AC_LIBTOOL_PICMODE],
|
||||
[_LT_SET_OPTION([LT_INIT], [pic-only])
|
||||
AC_DIAGNOSE([obsolete],
|
||||
[$0: Remove this warning and the call to _LT_SET_OPTION when you
|
||||
put the 'pic-only' option into LT_INIT's first parameter.])
|
||||
])
|
||||
|
||||
dnl aclocal-1.4 backwards compatibility:
|
||||
dnl AC_DEFUN([AC_LIBTOOL_PICMODE], [])
|
||||
|
||||
## ----------------- ##
|
||||
## LTDL_INIT Options ##
|
||||
## ----------------- ##
|
||||
|
||||
m4_define([_LTDL_MODE], [])
|
||||
LT_OPTION_DEFINE([LTDL_INIT], [nonrecursive],
|
||||
[m4_define([_LTDL_MODE], [nonrecursive])])
|
||||
LT_OPTION_DEFINE([LTDL_INIT], [recursive],
|
||||
[m4_define([_LTDL_MODE], [recursive])])
|
||||
LT_OPTION_DEFINE([LTDL_INIT], [subproject],
|
||||
[m4_define([_LTDL_MODE], [subproject])])
|
||||
|
||||
m4_define([_LTDL_TYPE], [])
|
||||
LT_OPTION_DEFINE([LTDL_INIT], [installable],
|
||||
[m4_define([_LTDL_TYPE], [installable])])
|
||||
LT_OPTION_DEFINE([LTDL_INIT], [convenience],
|
||||
[m4_define([_LTDL_TYPE], [convenience])])
|
124
trunk/3rdparty/gperftools-2-fit/m4/ltsugar.m4
vendored
Normal file
|
@ -0,0 +1,124 @@
|
|||
# ltsugar.m4 -- libtool m4 base layer. -*-Autoconf-*-
|
||||
#
|
||||
# Copyright (C) 2004-2005, 2007-2008, 2011-2015 Free Software
|
||||
# Foundation, Inc.
|
||||
# Written by Gary V. Vaughan, 2004
|
||||
#
|
||||
# This file is free software; the Free Software Foundation gives
|
||||
# unlimited permission to copy and/or distribute it, with or without
|
||||
# modifications, as long as this notice is preserved.
|
||||
|
||||
# serial 6 ltsugar.m4
|
||||
|
||||
# This is to help aclocal find these macros, as it can't see m4_define.
|
||||
AC_DEFUN([LTSUGAR_VERSION], [m4_if([0.1])])
|
||||
|
||||
|
||||
# lt_join(SEP, ARG1, [ARG2...])
|
||||
# -----------------------------
|
||||
# Produce ARG1SEPARG2...SEPARGn, omitting [] arguments and their
|
||||
# associated separator.
|
||||
# Needed until we can rely on m4_join from Autoconf 2.62, since all earlier
|
||||
# versions in m4sugar had bugs.
|
||||
m4_define([lt_join],
|
||||
[m4_if([$#], [1], [],
|
||||
[$#], [2], [[$2]],
|
||||
[m4_if([$2], [], [], [[$2]_])$0([$1], m4_shift(m4_shift($@)))])])
|
||||
m4_define([_lt_join],
|
||||
[m4_if([$#$2], [2], [],
|
||||
[m4_if([$2], [], [], [[$1$2]])$0([$1], m4_shift(m4_shift($@)))])])
|
||||
|
||||
|
||||
# lt_car(LIST)
|
||||
# lt_cdr(LIST)
|
||||
# ------------
|
||||
# Manipulate m4 lists.
|
||||
# These macros are necessary as long as will still need to support
|
||||
# Autoconf-2.59, which quotes differently.
|
||||
m4_define([lt_car], [[$1]])
|
||||
m4_define([lt_cdr],
|
||||
[m4_if([$#], 0, [m4_fatal([$0: cannot be called without arguments])],
|
||||
[$#], 1, [],
|
||||
[m4_dquote(m4_shift($@))])])
|
||||
m4_define([lt_unquote], $1)
|
||||
|
||||
|
||||
# lt_append(MACRO-NAME, STRING, [SEPARATOR])
|
||||
# ------------------------------------------
|
||||
# Redefine MACRO-NAME to hold its former content plus 'SEPARATOR''STRING'.
|
||||
# Note that neither SEPARATOR nor STRING are expanded; they are appended
|
||||
# to MACRO-NAME as is (leaving the expansion for when MACRO-NAME is invoked).
|
||||
# No SEPARATOR is output if MACRO-NAME was previously undefined (different
|
||||
# than defined and empty).
|
||||
#
|
||||
# This macro is needed until we can rely on Autoconf 2.62, since earlier
|
||||
# versions of m4sugar mistakenly expanded SEPARATOR but not STRING.
|
||||
m4_define([lt_append],
|
||||
[m4_define([$1],
|
||||
m4_ifdef([$1], [m4_defn([$1])[$3]])[$2])])
|
||||
|
||||
|
||||
|
||||
# lt_combine(SEP, PREFIX-LIST, INFIX, SUFFIX1, [SUFFIX2...])
|
||||
# ----------------------------------------------------------
|
||||
# Produce a SEP delimited list of all paired combinations of elements of
|
||||
# PREFIX-LIST with SUFFIX1 through SUFFIXn. Each element of the list
|
||||
# has the form PREFIXmINFIXSUFFIXn.
|
||||
# Needed until we can rely on m4_combine added in Autoconf 2.62.
|
||||
m4_define([lt_combine],
|
||||
[m4_if(m4_eval([$# > 3]), [1],
|
||||
[m4_pushdef([_Lt_sep], [m4_define([_Lt_sep], m4_defn([lt_car]))])]]dnl
|
||||
[[m4_foreach([_Lt_prefix], [$2],
|
||||
[m4_foreach([_Lt_suffix],
|
||||
]m4_dquote(m4_dquote(m4_shift(m4_shift(m4_shift($@)))))[,
|
||||
[_Lt_sep([$1])[]m4_defn([_Lt_prefix])[$3]m4_defn([_Lt_suffix])])])])])
|
||||
|
||||
|
||||
# lt_if_append_uniq(MACRO-NAME, VARNAME, [SEPARATOR], [UNIQ], [NOT-UNIQ])
|
||||
# -----------------------------------------------------------------------
|
||||
# Iff MACRO-NAME does not yet contain VARNAME, then append it (delimited
|
||||
# by SEPARATOR if supplied) and expand UNIQ, else NOT-UNIQ.
|
||||
m4_define([lt_if_append_uniq],
|
||||
[m4_ifdef([$1],
|
||||
[m4_if(m4_index([$3]m4_defn([$1])[$3], [$3$2$3]), [-1],
|
||||
[lt_append([$1], [$2], [$3])$4],
|
||||
[$5])],
|
||||
[lt_append([$1], [$2], [$3])$4])])
|
||||
|
||||
|
||||
# lt_dict_add(DICT, KEY, VALUE)
|
||||
# -----------------------------
|
||||
m4_define([lt_dict_add],
|
||||
[m4_define([$1($2)], [$3])])
|
||||
|
||||
|
||||
# lt_dict_add_subkey(DICT, KEY, SUBKEY, VALUE)
|
||||
# --------------------------------------------
|
||||
m4_define([lt_dict_add_subkey],
|
||||
[m4_define([$1($2:$3)], [$4])])
|
||||
|
||||
|
||||
# lt_dict_fetch(DICT, KEY, [SUBKEY])
|
||||
# ----------------------------------
|
||||
m4_define([lt_dict_fetch],
|
||||
[m4_ifval([$3],
|
||||
m4_ifdef([$1($2:$3)], [m4_defn([$1($2:$3)])]),
|
||||
m4_ifdef([$1($2)], [m4_defn([$1($2)])]))])
|
||||
|
||||
|
||||
# lt_if_dict_fetch(DICT, KEY, [SUBKEY], VALUE, IF-TRUE, [IF-FALSE])
|
||||
# -----------------------------------------------------------------
|
||||
m4_define([lt_if_dict_fetch],
|
||||
[m4_if(lt_dict_fetch([$1], [$2], [$3]), [$4],
|
||||
[$5],
|
||||
[$6])])
|
||||
|
||||
|
||||
# lt_dict_filter(DICT, [SUBKEY], VALUE, [SEPARATOR], KEY, [...])
|
||||
# --------------------------------------------------------------
|
||||
m4_define([lt_dict_filter],
|
||||
[m4_if([$5], [], [],
|
||||
[lt_join(m4_quote(m4_default([$4], [[, ]])),
|
||||
lt_unquote(m4_split(m4_normalize(m4_foreach(_Lt_key, lt_car([m4_shiftn(4, $@)]),
|
||||
[lt_if_dict_fetch([$1], _Lt_key, [$2], [$3], [_Lt_key ])])))))])[]dnl
|
||||
])
|
23
trunk/3rdparty/gperftools-2-fit/m4/ltversion.m4
vendored
Normal file
|
@ -0,0 +1,23 @@
|
|||
# ltversion.m4 -- version numbers -*- Autoconf -*-
|
||||
#
|
||||
# Copyright (C) 2004, 2011-2015 Free Software Foundation, Inc.
|
||||
# Written by Scott James Remnant, 2004
|
||||
#
|
||||
# This file is free software; the Free Software Foundation gives
|
||||
# unlimited permission to copy and/or distribute it, with or without
|
||||
# modifications, as long as this notice is preserved.
|
||||
|
||||
# @configure_input@
|
||||
|
||||
# serial 4179 ltversion.m4
|
||||
# This file is part of GNU Libtool
|
||||
|
||||
m4_define([LT_PACKAGE_VERSION], [2.4.6])
|
||||
m4_define([LT_PACKAGE_REVISION], [2.4.6])
|
||||
|
||||
AC_DEFUN([LTVERSION_VERSION],
|
||||
[macro_version='2.4.6'
|
||||
macro_revision='2.4.6'
|
||||
_LT_DECL(, macro_version, 0, [Which release of libtool.m4 was used?])
|
||||
_LT_DECL(, macro_revision, 0)
|
||||
])
|
99
trunk/3rdparty/gperftools-2-fit/m4/lt~obsolete.m4
vendored
Normal file
|
@ -0,0 +1,99 @@
|
|||
# lt~obsolete.m4 -- aclocal satisfying obsolete definitions. -*-Autoconf-*-
|
||||
#
|
||||
# Copyright (C) 2004-2005, 2007, 2009, 2011-2015 Free Software
|
||||
# Foundation, Inc.
|
||||
# Written by Scott James Remnant, 2004.
|
||||
#
|
||||
# This file is free software; the Free Software Foundation gives
|
||||
# unlimited permission to copy and/or distribute it, with or without
|
||||
# modifications, as long as this notice is preserved.
|
||||
|
||||
# serial 5 lt~obsolete.m4
|
||||
|
||||
# These exist entirely to fool aclocal when bootstrapping libtool.
|
||||
#
|
||||
# In the past libtool.m4 has provided macros via AC_DEFUN (or AU_DEFUN),
|
||||
# which have later been changed to m4_define as they aren't part of the
|
||||
# exported API, or moved to Autoconf or Automake where they belong.
|
||||
#
|
||||
# The trouble is, aclocal is a bit thick. It'll see the old AC_DEFUN
|
||||
# in /usr/share/aclocal/libtool.m4 and remember it, then when it sees us
|
||||
# using a macro with the same name in our local m4/libtool.m4 it'll
|
||||
# pull the old libtool.m4 in (it doesn't see our shiny new m4_define
|
||||
# and doesn't know about Autoconf macros at all.)
|
||||
#
|
||||
# So we provide this file, which has a silly filename so it's always
|
||||
# included after everything else. This provides aclocal with the
|
||||
# AC_DEFUNs it wants, but when m4 processes it, it doesn't do anything
|
||||
# because those macros already exist, or will be overwritten later.
|
||||
# We use AC_DEFUN over AU_DEFUN for compatibility with aclocal-1.6.
|
||||
#
|
||||
# Anytime we withdraw an AC_DEFUN or AU_DEFUN, remember to add it here.
|
||||
# Yes, that means every name once taken will need to remain here until
|
||||
# we give up compatibility with versions before 1.7, at which point
|
||||
# we need to keep only those names which we still refer to.
|
||||
|
||||
# This is to help aclocal find these macros, as it can't see m4_define.
|
||||
AC_DEFUN([LTOBSOLETE_VERSION], [m4_if([1])])
|
||||
|
||||
m4_ifndef([AC_LIBTOOL_LINKER_OPTION], [AC_DEFUN([AC_LIBTOOL_LINKER_OPTION])])
|
||||
m4_ifndef([AC_PROG_EGREP], [AC_DEFUN([AC_PROG_EGREP])])
|
||||
m4_ifndef([_LT_AC_PROG_ECHO_BACKSLASH], [AC_DEFUN([_LT_AC_PROG_ECHO_BACKSLASH])])
|
||||
m4_ifndef([_LT_AC_SHELL_INIT], [AC_DEFUN([_LT_AC_SHELL_INIT])])
|
||||
m4_ifndef([_LT_AC_SYS_LIBPATH_AIX], [AC_DEFUN([_LT_AC_SYS_LIBPATH_AIX])])
|
||||
m4_ifndef([_LT_PROG_LTMAIN], [AC_DEFUN([_LT_PROG_LTMAIN])])
|
||||
m4_ifndef([_LT_AC_TAGVAR], [AC_DEFUN([_LT_AC_TAGVAR])])
|
||||
m4_ifndef([AC_LTDL_ENABLE_INSTALL], [AC_DEFUN([AC_LTDL_ENABLE_INSTALL])])
|
||||
m4_ifndef([AC_LTDL_PREOPEN], [AC_DEFUN([AC_LTDL_PREOPEN])])
|
||||
m4_ifndef([_LT_AC_SYS_COMPILER], [AC_DEFUN([_LT_AC_SYS_COMPILER])])
|
||||
m4_ifndef([_LT_AC_LOCK], [AC_DEFUN([_LT_AC_LOCK])])
|
||||
m4_ifndef([AC_LIBTOOL_SYS_OLD_ARCHIVE], [AC_DEFUN([AC_LIBTOOL_SYS_OLD_ARCHIVE])])
|
||||
m4_ifndef([_LT_AC_TRY_DLOPEN_SELF], [AC_DEFUN([_LT_AC_TRY_DLOPEN_SELF])])
|
||||
m4_ifndef([AC_LIBTOOL_PROG_CC_C_O], [AC_DEFUN([AC_LIBTOOL_PROG_CC_C_O])])
|
||||
m4_ifndef([AC_LIBTOOL_SYS_HARD_LINK_LOCKS], [AC_DEFUN([AC_LIBTOOL_SYS_HARD_LINK_LOCKS])])
|
||||
m4_ifndef([AC_LIBTOOL_OBJDIR], [AC_DEFUN([AC_LIBTOOL_OBJDIR])])
|
||||
m4_ifndef([AC_LTDL_OBJDIR], [AC_DEFUN([AC_LTDL_OBJDIR])])
|
||||
m4_ifndef([AC_LIBTOOL_PROG_LD_HARDCODE_LIBPATH], [AC_DEFUN([AC_LIBTOOL_PROG_LD_HARDCODE_LIBPATH])])
|
||||
m4_ifndef([AC_LIBTOOL_SYS_LIB_STRIP], [AC_DEFUN([AC_LIBTOOL_SYS_LIB_STRIP])])
|
||||
m4_ifndef([AC_PATH_MAGIC], [AC_DEFUN([AC_PATH_MAGIC])])
|
||||
m4_ifndef([AC_PROG_LD_GNU], [AC_DEFUN([AC_PROG_LD_GNU])])
|
||||
m4_ifndef([AC_PROG_LD_RELOAD_FLAG], [AC_DEFUN([AC_PROG_LD_RELOAD_FLAG])])
|
||||
m4_ifndef([AC_DEPLIBS_CHECK_METHOD], [AC_DEFUN([AC_DEPLIBS_CHECK_METHOD])])
|
||||
m4_ifndef([AC_LIBTOOL_PROG_COMPILER_NO_RTTI], [AC_DEFUN([AC_LIBTOOL_PROG_COMPILER_NO_RTTI])])
|
||||
m4_ifndef([AC_LIBTOOL_SYS_GLOBAL_SYMBOL_PIPE], [AC_DEFUN([AC_LIBTOOL_SYS_GLOBAL_SYMBOL_PIPE])])
|
||||
m4_ifndef([AC_LIBTOOL_PROG_COMPILER_PIC], [AC_DEFUN([AC_LIBTOOL_PROG_COMPILER_PIC])])
|
||||
m4_ifndef([AC_LIBTOOL_PROG_LD_SHLIBS], [AC_DEFUN([AC_LIBTOOL_PROG_LD_SHLIBS])])
|
||||
m4_ifndef([AC_LIBTOOL_POSTDEP_PREDEP], [AC_DEFUN([AC_LIBTOOL_POSTDEP_PREDEP])])
|
||||
m4_ifndef([LT_AC_PROG_EGREP], [AC_DEFUN([LT_AC_PROG_EGREP])])
|
||||
m4_ifndef([LT_AC_PROG_SED], [AC_DEFUN([LT_AC_PROG_SED])])
|
||||
m4_ifndef([_LT_CC_BASENAME], [AC_DEFUN([_LT_CC_BASENAME])])
|
||||
m4_ifndef([_LT_COMPILER_BOILERPLATE], [AC_DEFUN([_LT_COMPILER_BOILERPLATE])])
|
||||
m4_ifndef([_LT_LINKER_BOILERPLATE], [AC_DEFUN([_LT_LINKER_BOILERPLATE])])
|
||||
m4_ifndef([_AC_PROG_LIBTOOL], [AC_DEFUN([_AC_PROG_LIBTOOL])])
|
||||
m4_ifndef([AC_LIBTOOL_SETUP], [AC_DEFUN([AC_LIBTOOL_SETUP])])
|
||||
m4_ifndef([_LT_AC_CHECK_DLFCN], [AC_DEFUN([_LT_AC_CHECK_DLFCN])])
|
||||
m4_ifndef([AC_LIBTOOL_SYS_DYNAMIC_LINKER], [AC_DEFUN([AC_LIBTOOL_SYS_DYNAMIC_LINKER])])
|
||||
m4_ifndef([_LT_AC_TAGCONFIG], [AC_DEFUN([_LT_AC_TAGCONFIG])])
|
||||
m4_ifndef([AC_DISABLE_FAST_INSTALL], [AC_DEFUN([AC_DISABLE_FAST_INSTALL])])
|
||||
m4_ifndef([_LT_AC_LANG_CXX], [AC_DEFUN([_LT_AC_LANG_CXX])])
|
||||
m4_ifndef([_LT_AC_LANG_F77], [AC_DEFUN([_LT_AC_LANG_F77])])
|
||||
m4_ifndef([_LT_AC_LANG_GCJ], [AC_DEFUN([_LT_AC_LANG_GCJ])])
|
||||
m4_ifndef([AC_LIBTOOL_LANG_C_CONFIG], [AC_DEFUN([AC_LIBTOOL_LANG_C_CONFIG])])
|
||||
m4_ifndef([_LT_AC_LANG_C_CONFIG], [AC_DEFUN([_LT_AC_LANG_C_CONFIG])])
|
||||
m4_ifndef([AC_LIBTOOL_LANG_CXX_CONFIG], [AC_DEFUN([AC_LIBTOOL_LANG_CXX_CONFIG])])
|
||||
m4_ifndef([_LT_AC_LANG_CXX_CONFIG], [AC_DEFUN([_LT_AC_LANG_CXX_CONFIG])])
|
||||
m4_ifndef([AC_LIBTOOL_LANG_F77_CONFIG], [AC_DEFUN([AC_LIBTOOL_LANG_F77_CONFIG])])
|
||||
m4_ifndef([_LT_AC_LANG_F77_CONFIG], [AC_DEFUN([_LT_AC_LANG_F77_CONFIG])])
|
||||
m4_ifndef([AC_LIBTOOL_LANG_GCJ_CONFIG], [AC_DEFUN([AC_LIBTOOL_LANG_GCJ_CONFIG])])
|
||||
m4_ifndef([_LT_AC_LANG_GCJ_CONFIG], [AC_DEFUN([_LT_AC_LANG_GCJ_CONFIG])])
|
||||
m4_ifndef([AC_LIBTOOL_LANG_RC_CONFIG], [AC_DEFUN([AC_LIBTOOL_LANG_RC_CONFIG])])
|
||||
m4_ifndef([_LT_AC_LANG_RC_CONFIG], [AC_DEFUN([_LT_AC_LANG_RC_CONFIG])])
|
||||
m4_ifndef([AC_LIBTOOL_CONFIG], [AC_DEFUN([AC_LIBTOOL_CONFIG])])
|
||||
m4_ifndef([_LT_AC_FILE_LTDLL_C], [AC_DEFUN([_LT_AC_FILE_LTDLL_C])])
|
||||
m4_ifndef([_LT_REQUIRED_DARWIN_CHECKS], [AC_DEFUN([_LT_REQUIRED_DARWIN_CHECKS])])
|
||||
m4_ifndef([_LT_AC_PROG_CXXCPP], [AC_DEFUN([_LT_AC_PROG_CXXCPP])])
|
||||
m4_ifndef([_LT_PREPARE_SED_QUOTE_VARS], [AC_DEFUN([_LT_PREPARE_SED_QUOTE_VARS])])
|
||||
m4_ifndef([_LT_PROG_ECHO_BACKSLASH], [AC_DEFUN([_LT_PROG_ECHO_BACKSLASH])])
|
||||
m4_ifndef([_LT_PROG_F77], [AC_DEFUN([_LT_PROG_F77])])
|
||||
m4_ifndef([_LT_PROG_FC], [AC_DEFUN([_LT_PROG_FC])])
|
||||
m4_ifndef([_LT_PROG_CXX], [AC_DEFUN([_LT_PROG_CXX])])
|
112
trunk/3rdparty/gperftools-2-fit/m4/pc_from_ucontext.m4
vendored
Normal file
|
@ -0,0 +1,112 @@
|
|||
# We want to access the "PC" (Program Counter) register from a struct
|
||||
# ucontext. Every system has its own way of doing that. We try all the
|
||||
# possibilities we know about. Note REG_PC should come first (REG_RIP
|
||||
# is also defined on solaris, but does the wrong thing).
|
||||
|
||||
# OpenBSD doesn't have ucontext.h, but we can get PC from ucontext_t
|
||||
# by using signal.h.
|
||||
|
||||
# The first argument of AC_PC_FROM_UCONTEXT will be invoked when we
|
||||
# cannot find a way to obtain PC from ucontext.
|
||||
|
||||
AC_DEFUN([AC_PC_FROM_UCONTEXT],
|
||||
[AC_CHECK_HEADERS(ucontext.h)
|
||||
# Redhat 7 has <sys/ucontext.h>, but it barfs if we #include it directly
|
||||
# (this was fixed in later redhats). <ucontext.h> works fine, so use that.
|
||||
if grep "Red Hat Linux release 7" /etc/redhat-release >/dev/null 2>&1; then
|
||||
AC_DEFINE(HAVE_SYS_UCONTEXT_H, 0, [<sys/ucontext.h> is broken on redhat 7])
|
||||
ac_cv_header_sys_ucontext_h=no
|
||||
else
|
||||
AC_CHECK_HEADERS(sys/ucontext.h) # ucontext on OS X 10.6 (at least)
|
||||
fi
|
||||
AC_CHECK_HEADERS(cygwin/signal.h) # ucontext on cywgin
|
||||
AC_CHECK_HEADERS(asm/ptrace.h) # get ptrace macros, e.g. PT_NIP
|
||||
AC_MSG_CHECKING([how to access the program counter from a struct ucontext])
|
||||
pc_fields=" uc_mcontext.gregs[[REG_PC]]" # Solaris x86 (32 + 64 bit)
|
||||
pc_fields="$pc_fields uc_mcontext.gregs[[REG_EIP]]" # Linux (i386)
|
||||
pc_fields="$pc_fields uc_mcontext.gregs[[REG_RIP]]" # Linux (x86_64)
|
||||
pc_fields="$pc_fields uc_mcontext.sc_ip" # Linux (ia64)
|
||||
pc_fields="$pc_fields uc_mcontext.pc" # Linux (mips)
|
||||
pc_fields="$pc_fields uc_mcontext.uc_regs->gregs[[PT_NIP]]" # Linux (ppc)
|
||||
pc_fields="$pc_fields uc_mcontext.__gregs[[REG_PC]]" # Linux (riscv64)
|
||||
pc_fields="$pc_fields uc_mcontext.psw.addr" # Linux (s390)
|
||||
pc_fields="$pc_fields uc_mcontext.gregs[[R15]]" # Linux (arm old [untested])
|
||||
pc_fields="$pc_fields uc_mcontext.arm_pc" # Linux (arm arch 5)
|
||||
pc_fields="$pc_fields uc_mcontext.cr0_hi" # Linux (e2k)
|
||||
pc_fields="$pc_fields uc_mcontext.gp_regs[[PT_NIP]]" # Suse SLES 11 (ppc64)
|
||||
pc_fields="$pc_fields uc_mcontext.mc_eip" # FreeBSD (i386)
|
||||
pc_fields="$pc_fields uc_mcontext.mc_srr0" # FreeBSD (powerpc, powerpc64)
|
||||
pc_fields="$pc_fields uc_mcontext.mc_rip" # FreeBSD (x86_64 [untested])
|
||||
pc_fields="$pc_fields uc_mcontext.__gregs[[_REG_EIP]]" # NetBSD (i386)
|
||||
pc_fields="$pc_fields uc_mcontext.__gregs[[_REG_RIP]]" # NetBSD (x86_64)
|
||||
pc_fields="$pc_fields uc_mcontext->ss.eip" # OS X (i386, <=10.4)
|
||||
pc_fields="$pc_fields uc_mcontext->__ss.__eip" # OS X (i386, >=10.5)
|
||||
pc_fields="$pc_fields uc_mcontext->ss.rip" # OS X (x86_64)
|
||||
pc_fields="$pc_fields uc_mcontext->__ss.__rip" # OS X (>=10.5 [untested])
|
||||
pc_fields="$pc_fields uc_mcontext->ss.srr0" # OS X (ppc, ppc64 [untested])
|
||||
pc_fields="$pc_fields uc_mcontext->__ss.__srr0" # OS X (>=10.5 [untested])
|
||||
pc_fields="$pc_fields uc_mcontext->__ss.__pc" # OS X (arm64)
|
||||
pc_field_found=false
|
||||
for pc_field in $pc_fields; do
|
||||
if ! $pc_field_found; then
|
||||
# Prefer sys/ucontext.h to ucontext.h, for OS X's sake.
|
||||
if test "x$ac_cv_header_cygwin_signal_h" = xyes; then
|
||||
AC_TRY_COMPILE([#define _GNU_SOURCE 1
|
||||
#include <cygwin/signal.h>],
|
||||
[ucontext_t u; return u.$pc_field == 0;],
|
||||
AC_DEFINE_UNQUOTED(PC_FROM_UCONTEXT, $pc_field,
|
||||
How to access the PC from a struct ucontext)
|
||||
AC_MSG_RESULT([$pc_field])
|
||||
pc_field_found=true)
|
||||
elif test "x$ac_cv_header_asm_ptrace_h" = xyes -a "x$ac_cv_header_sys_ucontext_h" = xyes; then
|
||||
AC_TRY_COMPILE([#define _GNU_SOURCE 1
|
||||
#include <asm/ptrace.h>
|
||||
#include <sys/ucontext.h>],
|
||||
[ucontext_t u; return u.$pc_field == 0;],
|
||||
AC_DEFINE_UNQUOTED(PC_FROM_UCONTEXT, $pc_field,
|
||||
How to access the PC from a struct ucontext)
|
||||
AC_MSG_RESULT([$pc_field])
|
||||
pc_field_found=true)
|
||||
elif test "x$ac_cv_header_sys_ucontext_h" = xyes; then
|
||||
AC_TRY_COMPILE([#define _GNU_SOURCE 1
|
||||
#include <sys/ucontext.h>],
|
||||
[ucontext_t u; return u.$pc_field == 0;],
|
||||
AC_DEFINE_UNQUOTED(PC_FROM_UCONTEXT, $pc_field,
|
||||
How to access the PC from a struct ucontext)
|
||||
AC_MSG_RESULT([$pc_field])
|
||||
pc_field_found=true)
|
||||
elif test "x$ac_cv_header_ucontext_h" = xyes; then
|
||||
AC_TRY_COMPILE([#define _GNU_SOURCE 1
|
||||
#include <ucontext.h>],
|
||||
[ucontext_t u; return u.$pc_field == 0;],
|
||||
AC_DEFINE_UNQUOTED(PC_FROM_UCONTEXT, $pc_field,
|
||||
How to access the PC from a struct ucontext)
|
||||
AC_MSG_RESULT([$pc_field])
|
||||
pc_field_found=true)
|
||||
else # hope some standard header gives it to us
|
||||
AC_TRY_COMPILE([],
|
||||
[ucontext_t u; return u.$pc_field == 0;],
|
||||
AC_DEFINE_UNQUOTED(PC_FROM_UCONTEXT, $pc_field,
|
||||
How to access the PC from a struct ucontext)
|
||||
AC_MSG_RESULT([$pc_field])
|
||||
pc_field_found=true)
|
||||
fi
|
||||
fi
|
||||
done
|
||||
if ! $pc_field_found; then
|
||||
pc_fields=" sc_eip" # OpenBSD (i386)
|
||||
pc_fields="$pc_fields sc_rip" # OpenBSD (x86_64)
|
||||
for pc_field in $pc_fields; do
|
||||
if ! $pc_field_found; then
|
||||
AC_TRY_COMPILE([#include <signal.h>],
|
||||
[ucontext_t u; return u.$pc_field == 0;],
|
||||
AC_DEFINE_UNQUOTED(PC_FROM_UCONTEXT, $pc_field,
|
||||
How to access the PC from a struct ucontext)
|
||||
AC_MSG_RESULT([$pc_field])
|
||||
pc_field_found=true)
|
||||
fi
|
||||
done
|
||||
fi
|
||||
if ! $pc_field_found; then
|
||||
[$1]
|
||||
fi])
|
19
trunk/3rdparty/gperftools-2-fit/m4/program_invocation_name.m4
vendored
Normal file
|
@ -0,0 +1,19 @@
|
|||
# We need to be careful to avoid having the reference to
|
||||
# program_invocation_name optimized out. We do that by
|
||||
# returning the value.
|
||||
|
||||
AC_DEFUN([AC_PROGRAM_INVOCATION_NAME],
|
||||
[AC_CACHE_CHECK(
|
||||
for program_invocation_name,
|
||||
ac_cv_have_program_invocation_name,
|
||||
AC_TRY_LINK([extern char* program_invocation_name;],
|
||||
[return *program_invocation_name;],
|
||||
[ac_cv_have_program_invocation_name=yes],
|
||||
[ac_cv_have_program_invocation_name=no])
|
||||
)
|
||||
if test "$ac_cv_have_program_invocation_name" = "yes"; then
|
||||
AC_DEFINE(HAVE_PROGRAM_INVOCATION_NAME, 1,
|
||||
[define if libc has program_invocation_name])
|
||||
fi
|
||||
])
|
||||
|
215
trunk/3rdparty/gperftools-2-fit/missing
vendored
Executable file
|
@ -0,0 +1,215 @@
|
|||
#! /bin/sh
|
||||
# Common wrapper for a few potentially missing GNU programs.
|
||||
|
||||
scriptversion=2018-03-07.03; # UTC
|
||||
|
||||
# Copyright (C) 1996-2020 Free Software Foundation, Inc.
|
||||
# Originally written by Fran,cois Pinard <pinard@iro.umontreal.ca>, 1996.
|
||||
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; either version 2, or (at your option)
|
||||
# any later version.
|
||||
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
|
||||
# As a special exception to the GNU General Public License, if you
|
||||
# distribute this file as part of a program that contains a
|
||||
# configuration script generated by Autoconf, you may include it under
|
||||
# the same distribution terms that you use for the rest of that program.
|
||||
|
||||
if test $# -eq 0; then
|
||||
echo 1>&2 "Try '$0 --help' for more information"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
case $1 in
|
||||
|
||||
--is-lightweight)
|
||||
# Used by our autoconf macros to check whether the available missing
|
||||
# script is modern enough.
|
||||
exit 0
|
||||
;;
|
||||
|
||||
--run)
|
||||
# Back-compat with the calling convention used by older automake.
|
||||
shift
|
||||
;;
|
||||
|
||||
-h|--h|--he|--hel|--help)
|
||||
echo "\
|
||||
$0 [OPTION]... PROGRAM [ARGUMENT]...
|
||||
|
||||
Run 'PROGRAM [ARGUMENT]...', returning a proper advice when this fails due
|
||||
to PROGRAM being missing or too old.
|
||||
|
||||
Options:
|
||||
-h, --help display this help and exit
|
||||
-v, --version output version information and exit
|
||||
|
||||
Supported PROGRAM values:
|
||||
aclocal autoconf autoheader autom4te automake makeinfo
|
||||
bison yacc flex lex help2man
|
||||
|
||||
Version suffixes to PROGRAM as well as the prefixes 'gnu-', 'gnu', and
|
||||
'g' are ignored when checking the name.
|
||||
|
||||
Send bug reports to <bug-automake@gnu.org>."
|
||||
exit $?
|
||||
;;
|
||||
|
||||
-v|--v|--ve|--ver|--vers|--versi|--versio|--version)
|
||||
echo "missing $scriptversion (GNU Automake)"
|
||||
exit $?
|
||||
;;
|
||||
|
||||
-*)
|
||||
echo 1>&2 "$0: unknown '$1' option"
|
||||
echo 1>&2 "Try '$0 --help' for more information"
|
||||
exit 1
|
||||
;;
|
||||
|
||||
esac
|
||||
|
||||
# Run the given program, remember its exit status.
|
||||
"$@"; st=$?
|
||||
|
||||
# If it succeeded, we are done.
|
||||
test $st -eq 0 && exit 0
|
||||
|
||||
# Also exit now if we it failed (or wasn't found), and '--version' was
|
||||
# passed; such an option is passed most likely to detect whether the
|
||||
# program is present and works.
|
||||
case $2 in --version|--help) exit $st;; esac
|
||||
|
||||
# Exit code 63 means version mismatch. This often happens when the user
|
||||
# tries to use an ancient version of a tool on a file that requires a
|
||||
# minimum version.
|
||||
if test $st -eq 63; then
|
||||
msg="probably too old"
|
||||
elif test $st -eq 127; then
|
||||
# Program was missing.
|
||||
msg="missing on your system"
|
||||
else
|
||||
# Program was found and executed, but failed. Give up.
|
||||
exit $st
|
||||
fi
|
||||
|
||||
perl_URL=https://www.perl.org/
|
||||
flex_URL=https://github.com/westes/flex
|
||||
gnu_software_URL=https://www.gnu.org/software
|
||||
|
||||
program_details ()
|
||||
{
|
||||
case $1 in
|
||||
aclocal|automake)
|
||||
echo "The '$1' program is part of the GNU Automake package:"
|
||||
echo "<$gnu_software_URL/automake>"
|
||||
echo "It also requires GNU Autoconf, GNU m4 and Perl in order to run:"
|
||||
echo "<$gnu_software_URL/autoconf>"
|
||||
echo "<$gnu_software_URL/m4/>"
|
||||
echo "<$perl_URL>"
|
||||
;;
|
||||
autoconf|autom4te|autoheader)
|
||||
echo "The '$1' program is part of the GNU Autoconf package:"
|
||||
echo "<$gnu_software_URL/autoconf/>"
|
||||
echo "It also requires GNU m4 and Perl in order to run:"
|
||||
echo "<$gnu_software_URL/m4/>"
|
||||
echo "<$perl_URL>"
|
||||
;;
|
||||
esac
|
||||
}
|
||||
|
||||
give_advice ()
|
||||
{
|
||||
# Normalize program name to check for.
|
||||
normalized_program=`echo "$1" | sed '
|
||||
s/^gnu-//; t
|
||||
s/^gnu//; t
|
||||
s/^g//; t'`
|
||||
|
||||
printf '%s\n' "'$1' is $msg."
|
||||
|
||||
configure_deps="'configure.ac' or m4 files included by 'configure.ac'"
|
||||
case $normalized_program in
|
||||
autoconf*)
|
||||
echo "You should only need it if you modified 'configure.ac',"
|
||||
echo "or m4 files included by it."
|
||||
program_details 'autoconf'
|
||||
;;
|
||||
autoheader*)
|
||||
echo "You should only need it if you modified 'acconfig.h' or"
|
||||
echo "$configure_deps."
|
||||
program_details 'autoheader'
|
||||
;;
|
||||
automake*)
|
||||
echo "You should only need it if you modified 'Makefile.am' or"
|
||||
echo "$configure_deps."
|
||||
program_details 'automake'
|
||||
;;
|
||||
aclocal*)
|
||||
echo "You should only need it if you modified 'acinclude.m4' or"
|
||||
echo "$configure_deps."
|
||||
program_details 'aclocal'
|
||||
;;
|
||||
autom4te*)
|
||||
echo "You might have modified some maintainer files that require"
|
||||
echo "the 'autom4te' program to be rebuilt."
|
||||
program_details 'autom4te'
|
||||
;;
|
||||
bison*|yacc*)
|
||||
echo "You should only need it if you modified a '.y' file."
|
||||
echo "You may want to install the GNU Bison package:"
|
||||
echo "<$gnu_software_URL/bison/>"
|
||||
;;
|
||||
lex*|flex*)
|
||||
echo "You should only need it if you modified a '.l' file."
|
||||
echo "You may want to install the Fast Lexical Analyzer package:"
|
||||
echo "<$flex_URL>"
|
||||
;;
|
||||
help2man*)
|
||||
echo "You should only need it if you modified a dependency" \
|
||||
"of a man page."
|
||||
echo "You may want to install the GNU Help2man package:"
|
||||
echo "<$gnu_software_URL/help2man/>"
|
||||
;;
|
||||
makeinfo*)
|
||||
echo "You should only need it if you modified a '.texi' file, or"
|
||||
echo "any other file indirectly affecting the aspect of the manual."
|
||||
echo "You might want to install the Texinfo package:"
|
||||
echo "<$gnu_software_URL/texinfo/>"
|
||||
echo "The spurious makeinfo call might also be the consequence of"
|
||||
echo "using a buggy 'make' (AIX, DU, IRIX), in which case you might"
|
||||
echo "want to install GNU make:"
|
||||
echo "<$gnu_software_URL/make/>"
|
||||
;;
|
||||
*)
|
||||
echo "You might have modified some files without having the proper"
|
||||
echo "tools for further handling them. Check the 'README' file, it"
|
||||
echo "often tells you about the needed prerequisites for installing"
|
||||
echo "this package. You may also peek at any GNU archive site, in"
|
||||
echo "case some other package contains this missing '$1' program."
|
||||
;;
|
||||
esac
|
||||
}
|
||||
|
||||
give_advice "$1" | sed -e '1s/^/WARNING: /' \
|
||||
-e '2,$s/^/ /' >&2
|
||||
|
||||
# Propagate the correct exit status (expected to be 127 for a program
|
||||
# not found, 63 for a program that failed due to version mismatch).
|
||||
exit $st
|
||||
|
||||
# Local variables:
|
||||
# eval: (add-hook 'before-save-hook 'time-stamp)
|
||||
# time-stamp-start: "scriptversion="
|
||||
# time-stamp-format: "%:y-%02m-%02d.%02H"
|
||||
# time-stamp-time-zone: "UTC0"
|
||||
# time-stamp-end: "; # UTC"
|
||||
# End:
|
74
trunk/3rdparty/gperftools-2-fit/packages/deb.sh
vendored
Executable file
|
@ -0,0 +1,74 @@
|
|||
#!/bin/bash -e
|
||||
|
||||
# This takes one commandline argument, the name of the package. If no
|
||||
# name is given, then we'll end up just using the name associated with
|
||||
# an arbitrary .tar.gz file in the rootdir. That's fine: there's probably
|
||||
# only one.
|
||||
#
|
||||
# Run this from the 'packages' directory, just under rootdir
|
||||
|
||||
## Set LIB to lib if exporting a library, empty-string else
|
||||
LIB=
|
||||
#LIB=lib
|
||||
|
||||
PACKAGE="$1"
|
||||
VERSION="$2"
|
||||
|
||||
# We can only build Debian packages, if the Debian build tools are installed
|
||||
if [ \! -x /usr/bin/debuild ]; then
|
||||
echo "Cannot find /usr/bin/debuild. Not building Debian packages." 1>&2
|
||||
exit 0
|
||||
fi
|
||||
|
||||
# Double-check we're in the packages directory, just under rootdir
|
||||
if [ \! -r ../Makefile -a \! -r ../INSTALL ]; then
|
||||
echo "Must run $0 in the 'packages' directory, under the root directory." 1>&2
|
||||
echo "Also, you must run \"make dist\" before running this script." 1>&2
|
||||
exit 0
|
||||
fi
|
||||
|
||||
# Find the top directory for this package
|
||||
topdir="${PWD%/*}"
|
||||
|
||||
# Find the tar archive built by "make dist"
|
||||
archive="${PACKAGE}-${VERSION}"
|
||||
archive_with_underscore="${PACKAGE}_${VERSION}"
|
||||
if [ -z "${archive}" ]; then
|
||||
echo "Cannot find ../$PACKAGE*.tar.gz. Run \"make dist\" first." 1>&2
|
||||
exit 0
|
||||
fi
|
||||
|
||||
# Create a pristine directory for building the Debian package files
|
||||
trap 'rm -rf '`pwd`/tmp'; exit $?' EXIT SIGHUP SIGINT SIGTERM
|
||||
|
||||
rm -rf tmp
|
||||
mkdir -p tmp
|
||||
cd tmp
|
||||
|
||||
# Debian has very specific requirements about the naming of build
|
||||
# directories, and tar archives. It also wants to write all generated
|
||||
# packages to the parent of the source directory. We accommodate these
|
||||
# requirements by building directly from the tar file.
|
||||
ln -s "${topdir}/${archive}.tar.gz" "${LIB}${archive}.orig.tar.gz"
|
||||
# Some version of debuilder want foo.orig.tar.gz with _ between versions.
|
||||
ln -s "${topdir}/${archive}.tar.gz" "${LIB}${archive_with_underscore}.orig.tar.gz"
|
||||
tar zfx "${LIB}${archive}.orig.tar.gz"
|
||||
[ -n "${LIB}" ] && mv "${archive}" "${LIB}${archive}"
|
||||
cd "${LIB}${archive}"
|
||||
# This is one of those 'specific requirements': where the deb control files live
|
||||
cp -a "packages/deb" "debian"
|
||||
|
||||
# Now, we can call Debian's standard build tool
|
||||
debuild -uc -us
|
||||
cd ../.. # get back to the original top-level dir
|
||||
|
||||
# We'll put the result in a subdirectory that's named after the OS version
|
||||
# we've made this .deb file for.
|
||||
destdir="debian-$(cat /etc/debian_version 2>/dev/null || echo UNKNOWN)"
|
||||
|
||||
rm -rf "$destdir"
|
||||
mkdir -p "$destdir"
|
||||
mv $(find tmp -mindepth 1 -maxdepth 1 -type f) "$destdir"
|
||||
|
||||
echo
|
||||
echo "The Debian package files are located in $PWD/$destdir"
|
7
trunk/3rdparty/gperftools-2-fit/packages/deb/README
vendored
Normal file
|
@ -0,0 +1,7 @@
|
|||
The list of files here isn't complete. For a step-by-step guide on
|
||||
how to set this package up correctly, check out
|
||||
http://www.debian.org/doc/maint-guide/
|
||||
|
||||
Most of the files that are in this directory are boilerplate.
|
||||
However, you may need to change the list of binary-arch dependencies
|
||||
in 'rules'.
|
208
trunk/3rdparty/gperftools-2-fit/packages/deb/changelog
vendored
Normal file
|
@ -0,0 +1,208 @@
|
|||
gperftools (2.1-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- gperftools Contributors <google-perftools@googlegroups.com> Tue, 30 Jul 2013 11:51:13 +0300
|
||||
|
||||
gperftools (2.0.99-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- gperftools Contributors <google-perftools@googlegroups.com> Sat, 20 Jul 2013 14:21:10 -0700
|
||||
|
||||
gperftools (2.0-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
* Package renamed from google-perftools to gperftools.
|
||||
|
||||
-- Google Inc. and others <google-perftools@googlegroups.com> Fri, 03 Feb 2012 15:40:45 -0800
|
||||
|
||||
google-perftools (1.10-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Tue, 31 Jan 2012 10:43:50 -0800
|
||||
|
||||
google-perftools (1.9-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Thu, 22 Dec 2011 16:22:45 -0800
|
||||
|
||||
google-perftools (1.8-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Fri, 15 Jul 2011 16:10:51 -0700
|
||||
|
||||
google-perftools (1.7-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Fri, 04 Feb 2011 15:54:31 -0800
|
||||
|
||||
google-perftools (1.6-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Thu, 05 Aug 2010 12:48:03 -0700
|
||||
|
||||
google-perftools (1.5-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Tue, 19 Jan 2010 14:46:12 -0800
|
||||
|
||||
google-perftools (1.4-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Thu, 10 Sep 2009 13:51:15 -0700
|
||||
|
||||
google-perftools (1.3-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Tue, 09 Jun 2009 18:19:06 -0700
|
||||
|
||||
google-perftools (1.2-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Fri, 17 Apr 2009 16:40:48 -0700
|
||||
|
||||
google-perftools (1.1-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Wed, 11 Mar 2009 11:25:34 -0700
|
||||
|
||||
google-perftools (1.0-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Tue, 06 Jan 2009 13:58:56 -0800
|
||||
|
||||
google-perftools (1.0rc1-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Thu, 11 Dec 2008 16:01:32 -0800
|
||||
|
||||
google-perftools (0.99.1-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Sat, 20 Sep 2008 09:37:18 -0700
|
||||
|
||||
google-perftools (0.99-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Thu, 18 Sep 2008 16:00:27 -0700
|
||||
|
||||
google-perftools (0.98-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Mon, 09 Jun 2008 16:47:03 -0700
|
||||
|
||||
google-perftools (0.97-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Mon, 21 Apr 2008 15:20:52 -0700
|
||||
|
||||
google-perftools (0.96-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Tue, 18 Mar 2008 14:30:44 -0700
|
||||
|
||||
google-perftools (0.95-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Tue, 12 Feb 2008 12:28:32 -0800
|
||||
|
||||
google-perftools (0.94-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Thu, 29 Nov 2007 07:59:43 -0800
|
||||
|
||||
google-perftools (0.93-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Fri, 17 Aug 2007 12:32:56 -0700
|
||||
|
||||
google-perftools (0.92-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Tue, 17 Jul 2007 22:26:27 -0700
|
||||
|
||||
google-perftools (0.91-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Wed, 18 Apr 2007 16:43:55 -0700
|
||||
|
||||
google-perftools (0.90-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Fri, 13 Apr 2007 14:50:51 -0700
|
||||
|
||||
google-perftools (0.8-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Wed, 14 Jun 2006 15:11:14 -0700
|
||||
|
||||
google-perftools (0.7-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Thu, 13 Apr 2006 20:59:09 -0700
|
||||
|
||||
google-perftools (0.6-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Fri, 27 Jan 2006 14:04:27 -0800
|
||||
|
||||
google-perftools (0.5-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Mon, Nov 14 17:28:59 2005 -0800
|
||||
|
||||
google-perftools (0.4-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Wed, 26 Oct 2005 15:19:16 -0700
|
||||
|
||||
google-perftools (0.3-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Fri, 24 Jun 2005 18:02:26 -0700
|
||||
|
||||
google-perftools (0.2-1) unstable; urgency=low
|
||||
|
||||
* New upstream release.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Tue, 31 May 2005 08:14:38 -0700
|
||||
|
||||
google-perftools (0.1-1) unstable; urgency=low
|
||||
|
||||
* Initial release.
|
||||
The google-perftools package contains some utilities to improve
|
||||
and analyze the performance of C++ programs. This includes an
|
||||
optimized thread-caching malloc() and cpu and heap profiling
|
||||
utilities.
|
||||
|
||||
-- Google Inc. <opensource@google.com> Fri, 11 Mar 2005 08:07:33 -0800
|
1
trunk/3rdparty/gperftools-2-fit/packages/deb/compat
vendored
Normal file
|
@ -0,0 +1 @@
|
|||
4
|
25
trunk/3rdparty/gperftools-2-fit/packages/deb/control
vendored
Normal file
|
@ -0,0 +1,25 @@
|
|||
Source: gperftools
|
||||
Priority: optional
|
||||
Maintainer: gperftools Contributors <google-perftools@googlegroups.com>
|
||||
Build-Depends: debhelper (>= 4.0.0), binutils
|
||||
Standards-Version: 3.6.1
|
||||
|
||||
Package: libgperftools-dev
|
||||
Section: libdevel
|
||||
Architecture: any
|
||||
Depends: libgperftools0 (= ${Source-Version})
|
||||
Description: libraries for CPU and heap analysis, plus an efficient thread-caching malloc
|
||||
The gperftools package contains some utilities to improve and
|
||||
analyze the performance of C++ programs. This includes an optimized
|
||||
thread-caching malloc() and cpu and heap profiling utilities. The
|
||||
devel package contains static and debug libraries and header files
|
||||
for developing applications that use the gperftools package.
|
||||
|
||||
Package: libgperftools0
|
||||
Section: libs
|
||||
Architecture: any
|
||||
Depends: ${shlibs:Depends}
|
||||
Description: libraries for CPU and heap analysis, plus an efficient thread-caching malloc
|
||||
The gperftools package contains some utilities to improve and
|
||||
analyze the performance of C++ programs. This includes an optimized
|
||||
thread-caching malloc() and cpu and heap profiling utilities.
|
38
trunk/3rdparty/gperftools-2-fit/packages/deb/copyright
vendored
Normal file
|
@ -0,0 +1,38 @@
|
|||
This package was debianized by gperftools Contributors <google-perftools@googlegroups.com>
|
||||
on Sat, 20 Jul 2013 14:21:10 -0700.
|
||||
|
||||
It was downloaded from http://code.google.com/p/gperftools/downloads/list
|
||||
|
||||
Upstream Author: google-perftools@googlegroups.com
|
||||
|
||||
Copyright (c) 2005, Google Inc.
|
||||
All rights reserved.
|
||||
|
||||
Copyright (c) 2013, gperftools Contributors
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions are
|
||||
met:
|
||||
|
||||
* Redistributions of source code must retain the above copyright
|
||||
notice, this list of conditions and the following disclaimer.
|
||||
* Redistributions in binary form must reproduce the above
|
||||
copyright notice, this list of conditions and the following disclaimer
|
||||
in the documentation and/or other materials provided with the
|
||||
distribution.
|
||||
* Neither the name of Google Inc. nor the names of its
|
||||
contributors may be used to endorse or promote products derived from
|
||||
this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
||||
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
||||
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
||||
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
|
||||
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
||||
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
47
trunk/3rdparty/gperftools-2-fit/packages/deb/docs
vendored
Normal file
|
@ -0,0 +1,47 @@
|
|||
AUTHORS
|
||||
COPYING
|
||||
ChangeLog
|
||||
INSTALL
|
||||
NEWS
|
||||
README
|
||||
TODO
|
||||
docs/cpuprofile.html
|
||||
docs/cpuprofile-fileformat.html
|
||||
docs/designstyle.css
|
||||
docs/heap-example1.png
|
||||
docs/heap_checker.html
|
||||
docs/heapprofile.html
|
||||
docs/index.html
|
||||
docs/overview.gif
|
||||
docs/pageheap.gif
|
||||
docs/pprof-test-big.gif
|
||||
docs/pprof-test.gif
|
||||
docs/pprof-vsnprintf-big.gif
|
||||
docs/pprof-vsnprintf.gif
|
||||
docs/pprof.1
|
||||
docs/pprof_remote_servers.html
|
||||
docs/spanmap.gif
|
||||
docs/t-test1.times.txt
|
||||
docs/tcmalloc-opspercpusec.vs.threads.1024.bytes.png
|
||||
docs/tcmalloc-opspercpusec.vs.threads.128.bytes.png
|
||||
docs/tcmalloc-opspercpusec.vs.threads.131072.bytes.png
|
||||
docs/tcmalloc-opspercpusec.vs.threads.16384.bytes.png
|
||||
docs/tcmalloc-opspercpusec.vs.threads.2048.bytes.png
|
||||
docs/tcmalloc-opspercpusec.vs.threads.256.bytes.png
|
||||
docs/tcmalloc-opspercpusec.vs.threads.32768.bytes.png
|
||||
docs/tcmalloc-opspercpusec.vs.threads.4096.bytes.png
|
||||
docs/tcmalloc-opspercpusec.vs.threads.512.bytes.png
|
||||
docs/tcmalloc-opspercpusec.vs.threads.64.bytes.png
|
||||
docs/tcmalloc-opspercpusec.vs.threads.65536.bytes.png
|
||||
docs/tcmalloc-opspercpusec.vs.threads.8192.bytes.png
|
||||
docs/tcmalloc-opspersec.vs.size.1.threads.png
|
||||
docs/tcmalloc-opspersec.vs.size.12.threads.png
|
||||
docs/tcmalloc-opspersec.vs.size.16.threads.png
|
||||
docs/tcmalloc-opspersec.vs.size.2.threads.png
|
||||
docs/tcmalloc-opspersec.vs.size.20.threads.png
|
||||
docs/tcmalloc-opspersec.vs.size.3.threads.png
|
||||
docs/tcmalloc-opspersec.vs.size.4.threads.png
|
||||
docs/tcmalloc-opspersec.vs.size.5.threads.png
|
||||
docs/tcmalloc-opspersec.vs.size.8.threads.png
|
||||
docs/tcmalloc.html
|
||||
docs/threadheap.gif
|