GT-3481 - Gnu Demangler - Initial upgrade to v2.33.1

This commit is contained in:
dragonmacher 2020-01-27 15:28:17 -05:00
parent 16f050f901
commit 54af47adab
42 changed files with 20515 additions and 5456 deletions

View file

@ -91,7 +91,8 @@ model {
binaries {
all{ b ->
if (toolChain in Gcc) {
cCompiler.args "-DMAIN_CPLUS_DEM"
cCompiler.args "-DSTANDALONE_DEMANGLER"
cCompiler.args "-DHAVE_STDLIB_H"
cCompiler.args "-DHAVE_STRING_H"
if (targetPlatform.operatingSystem.linux) {
@ -100,12 +101,12 @@ model {
}
else if (toolChain in VisualCpp) {
cCompiler.args "/D_CONSOLE"
cCompiler.args "/DMAIN_CPLUS_DEM"
cCompiler.args "-DSTANDALONE_DEMANGLER"
cCompiler.args "-DHAVE_STDLIB_H"
cCompiler.args "-DHAVE_STRING_H"
}
else if (toolChain in Clang) {
cCompiler.args "-DMAIN_CPLUS_DEM"
cCompiler.args "-DSTANDALONE_DEMANGLER"
cCompiler.args "-DHAVE_STDLIB_H"
cCompiler.args "-DHAVE_STRING_H"
if (targetPlatform.operatingSystem.linux) {

View file

@ -8,3 +8,4 @@ Module.manifest||Public Domain||||END|
build.gradle||Public Domain||||END|
settings.gradle||Public Domain||||END|
src/demangler_gnu/README.txt||Public Domain||||END|
src/demangler_gnu_v2.24/README.txt||GHIDRA||||END|

View file

@ -1,7 +1,8 @@
PURPOSE
This is a readme file to note the changes made to the binutils-2.24 source
code in order for Ghidra to build its GNU demangler.
This is a readme file to note the changes made to the binutils-2.33.1 source
code in to build its GNU demangler. The files in this directory are used to create a demangling
utility during the full build process.
@ -23,29 +24,11 @@ Windows, such as MinGW.
CHANGES TO BINUTILS SOURCE
cplus-dem.c
cp-demangle.c
To this file was added about 400 lines of source code. Previously, this file contained a
main method that we used to build our stand alone demangler. The current version of
binutils does not have this main method. Instead, binutils has only a main method in
cp-demangle.c for building the stand alone demangler. The c++filt utility is created using
a main method inside of cxxfilt.c. We could not build that utility without using the
more complicated build system mentioned above.
In order to gain full functionality contained in the c++filt utility, we copied the main
method from cxxfilt.c and placed it, along with supporting methods, into cplus-dem.c. This
allows us to perform a simple build of the stand alone demangler, with less source files
required.
cp-demangle.c *
This file contains a small, two-line change to send a newline character ('\n') along with
a flush to the output stream. Without this change, the program, when called repeatedly from
Ghidra would eventually hang. This is due to the nature of how Ghidra reads results in a
line-oriented fashion.
*This change is no longer used, as we do not use the main method inside of this file, but have
switched to the main method we made and placed into cplus-dem.c.
This file contains a small, one-line change to flush to the standard output stream. Without
this change, the program, when called repeatedly from Java would hang as it attempts to read
characters that are buffered on the native side.
@ -53,42 +36,46 @@ switched to the main method we made and placed into cplus-dem.c.
UPDATING
If we ever wish to update to a newer version of binutils, then we will need to re-copy the files
in this directory and then rebuild the main method we created inside of cplus-dem.c. That is,
unless at least one of the following changes happens:
in this directory. That is, unless at least one of the following changes happens:
1) the stand alone demangler in cp-demangle has full c++filt support, or
2) binutils has put the main method back inside cplus-dem.c, or
3) building a stand alone c++filt is simple enough that we can do it on each platform, or
4) we decide to build the entire binutils suite and use the full c++filt binary.
1) building a stand alone c++filt is simple enough that we can do it on each platform, or
2) we decide to build the entire binutils suite and use the full c++filt binary.
SOURCE FILES NEEDED BY OS
SOURCE FILES
binutils/libiberty/alloca.c
binutils/libiberty/argv.c
binutils/libiberty/cp-demangle.c
binutils/libiberty/cplus-dem.c
binutils/libiberty/d-demangle.c
binutils/libiberty/dyn-string.c
binutils/libiberty/getopt.c
binutils/libiberty/getopt1.c
binutils/libiberty/rust-demangle.c
binutils/libiberty/safe-ctype.c
binutils/libiberty/xexit.c
binutils/libiberty/xstrdup.c
binutils/include/ansidecl.h
binutils/libiberty/cp-demangle.h
binutils/include/demangle.h
binutils/include/dyn-string.h
binutils/include/getopt.h
binutils/include/libiberty.h
binutils/libiberty/rust-demangle.h
binutils/include/safe-ctype.h
*nix / Mac
This file is created to add minor missing dependencies.
ansidecl.h
argv.c
cp-demangle.c
cp-demangle.h
cplus-dem.c
demangle.h
dyn-string.c
dyn-string.h
getopt.c
getopt.h
libiberty.h
safe-ctype.c
safe-ctype.h
xexit.c
xstrdup.c
WINDOWS
missing.c
alloca.c
getopt1.c
LICENSE
The files listed above are licensed by using the file header or the COPYING or COPYING.LIB file
listed in the original source directory of binutils.

View file

@ -1,6 +1,5 @@
/* ###
* IP: LGPL 2.1
* REVIEWED: YES
* NOTE: license is not in file, but in the directory from whence it came: binutils-2.24/libiberty/COPYING.LIB
*/
/* alloca.c -- allocate automatically reclaimed memory

View file

@ -1,10 +1,9 @@
/* ###
* IP: LGPL 2.1
* REVIEWED: YES
* NOTE: from binutils 2.24
* NOTE: See binutils/libiberty/COPYING.LIB
*/
/* Create and destroy argument vectors (argv's)
Copyright (C) 1992, 2001, 2010, 2012 Free Software Foundation, Inc.
Copyright (C) 1992-2019 Free Software Foundation, Inc.
Written by Fred Fish @ Cygnus Support
This file is part of the libiberty library.
@ -40,6 +39,13 @@ Boston, MA 02110-1301, USA. */
#include <string.h>
#include <stdlib.h>
#include <stdio.h>
#include <sys/types.h>
#ifdef HAVE_UNISTD_H
#include <unistd.h>
#endif
#if HAVE_SYS_STAT_H
#include <sys/stat.h>
#endif
#ifndef NULL
#define NULL 0
@ -54,7 +60,7 @@ Boston, MA 02110-1301, USA. */
/*
@deftypefn Extension char** dupargv (char **@var{vector})
@deftypefn Extension char** dupargv (char * const *@var{vector})
Duplicate an argument vector. Simply scans through @var{vector},
duplicating each argument until the terminating @code{NULL} is found.
@ -67,7 +73,7 @@ argument vector.
*/
char **
dupargv (char **argv)
dupargv (char * const *argv)
{
int argc;
char **copy;
@ -81,11 +87,7 @@ dupargv (char **argv)
/* the strings */
for (argc = 0; argv[argc] != NULL; argc++)
{
int len = strlen (argv[argc]);
copy[argc] = (char *) xmalloc (len + 1);
strcpy (copy[argc], argv[argc]);
}
copy[argc] = xstrdup (argv[argc]);
copy[argc] = NULL;
return copy;
}
@ -288,7 +290,7 @@ char **buildargv (const char *input)
/*
@deftypefn Extension int writeargv (const char **@var{argv}, FILE *@var{file})
@deftypefn Extension int writeargv (char * const *@var{argv}, FILE *@var{file})
Write each member of ARGV, handling all necessary quoting, to the file
named by FILE, separated by whitespace. Return 0 on success, non-zero
@ -299,7 +301,7 @@ if an error occurred while writing to FILE.
*/
int
writeargv (char **argv, FILE *f)
writeargv (char * const *argv, FILE *f)
{
int status = 0;
@ -369,8 +371,8 @@ expandargv (int *argcp, char ***argvp)
{
/* The argument we are currently processing. */
int i = 0;
/* Non-zero if ***argvp has been dynamically allocated. */
int argv_dynamic = 0;
/* To check if ***argvp has been dynamically allocated. */
char ** const original_argv = *argvp;
/* Limit the number of response files that we parse in order
to prevent infinite recursion. */
unsigned int iteration_limit = 2000;
@ -396,6 +398,9 @@ expandargv (int *argcp, char ***argvp)
char **file_argv;
/* The number of options read from the response file, if any. */
size_t file_argc;
#ifdef S_ISDIR
struct stat sb;
#endif
/* We are only interested in options of the form "@file". */
filename = (*argvp)[i];
if (filename[0] != '@')
@ -406,6 +411,15 @@ expandargv (int *argcp, char ***argvp)
fprintf (stderr, "%s: error: too many @-files encountered\n", (*argvp)[0]);
xexit (1);
}
#ifdef S_ISDIR
if (stat (filename+1, &sb) < 0)
continue;
if (S_ISDIR(sb.st_mode))
{
fprintf (stderr, "%s: error: @-file refers to a directory\n", (*argvp)[0]);
xexit (1);
}
#endif
/* Read the contents of the file. */
f = fopen (++filename, "r");
if (!f)
@ -439,12 +453,14 @@ expandargv (int *argcp, char ***argvp)
/* Parse the string. */
file_argv = buildargv (buffer);
/* If *ARGVP is not already dynamically allocated, copy it. */
if (!argv_dynamic)
if (*argvp == original_argv)
*argvp = dupargv (*argvp);
/* Count the number of arguments. */
file_argc = 0;
while (file_argv[file_argc])
++file_argc;
/* Free the original option's memory. */
free ((*argvp)[i]);
/* Now, insert FILE_ARGV into ARGV. The "+1" below handles the
NULL terminator at the end of ARGV. */
*argvp = ((char **)
@ -472,7 +488,7 @@ expandargv (int *argcp, char ***argvp)
/*
@deftypefn Extension int countargv (char **@var{argv})
@deftypefn Extension int countargv (char * const *@var{argv})
Return the number of elements in @var{argv}.
Returns zero if @var{argv} is NULL.
@ -482,7 +498,7 @@ Returns zero if @var{argv} is NULL.
*/
int
countargv (char **argv)
countargv (char * const *argv)
{
int argc;

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

View file

@ -1,9 +1,9 @@
/* ###
* IP: GPL 3 Linking Permitted
* REVIEWED: YES
* NOTE: See binutils/include/COPYING3
*/
/* An abstract string datatype.
Copyright (C) 1998, 1999, 2000, 2002, 2004 Free Software Foundation, Inc.
Copyright (C) 1998-2019 Free Software Foundation, Inc.
Contributed by Mark Mitchell (mark@markmitchell.com).
This file is part of GNU CC.

View file

@ -1,14 +1,13 @@
/* ###
* IP: GPL 3
* REVIEWED: YES
* NOTE: See binutils/include/COPYING3
*/
/* Getopt for GNU.
NOTE: getopt is now part of the C library, so if you don't know what
"Keep this file name-space clean" means, talk to drepper@gnu.org
before changing it!
Copyright (C) 1987, 1988, 1989, 1990, 1991, 1992, 1993, 1994, 1995,
1996, 1997, 1998, 2005 Free Software Foundation, Inc.
Copyright (C) 1987-2019 Free Software Foundation, Inc.
NOTE: This source is derived from an old version taken from the GNU C
Library (glibc).

View file

@ -1,10 +1,9 @@
/* ###
* IP: GPL 3
* REVIEWED: YES
* NOTE: See binutils/include/COPYING3
*/
/* getopt_long and getopt_long_only entry points for GNU getopt.
Copyright (C) 1987,88,89,90,91,92,93,94,96,97,98,2005
Free Software Foundation, Inc.
Copyright (C) 1987-2019 Free Software Foundation, Inc.
NOTE: This source is derived from an old version taken from the GNU C
Library (glibc).

View file

@ -0,0 +1,75 @@
/* ###
* IP: LGPL 2.1
* NOTE: Code copied from older version of cplus-dem.c that Ghidra had modified
*/
/*
Copyright (C) 2003-2019 Free Software Foundation, Inc.
This file exists to provide code missing from sibling files in this directory.
In addition to the permissions in the GNU Library General Public
License, the Free Software Foundation gives you unlimited permission
to link the compiled version of this file into combinations with other
programs, and to distribute those combinations without any restriction
coming from the use of this file. (The Library Public License
restrictions do apply in other respects; for example, they cover
modification of the file, and distribution when not linked into a
combined executable.)
Libiberty 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
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with libiberty; see the file COPYING.LIB. If
not, write to the Free Software Foundation, Inc., 51 Franklin Street - Fifth Floor,
Boston, MA 02110-1301, USA.
CHANGE NOTICE:
This file was created on January 22nd, 2020:
-This code was copied and modified from a previous version of libiberty
*/
#include <sys/types.h>
#include <stdio.h>
#ifdef HAVE_STDLIB_H
#include <stdlib.h>
#else
void * malloc ();
void * realloc ();
#endif
static void
fatal (str)
const char *str;
{
fprintf (stderr, "%s\n", str);
exit (1);
}
void *
xmalloc (size)
size_t size;
{
register void * value = malloc (size);
if (value == 0)
fatal ("virtual memory exhausted");
return value;
}
void *
xrealloc (ptr, size)
size_t size;
{
register void * value = realloc (ptr, size);
if (value == 0)
fatal ("virtual memory exhausted");
return value;
}

View file

@ -0,0 +1,353 @@
/* ###
* IP: LGPL 2.1
* NOTE: See binutils/libiberty/COPYING.LIB
*/
/* Demangler for the Rust programming language
Copyright (C) 2016-2019 Free Software Foundation, Inc.
Written by David Tolnay (dtolnay@gmail.com).
This file is part of the libiberty library.
Libiberty is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
In addition to the permissions in the GNU Library General Public
License, the Free Software Foundation gives you unlimited permission
to link the compiled version of this file into combinations with other
programs, and to distribute those combinations without any restriction
coming from the use of this file. (The Library Public License
restrictions do apply in other respects; for example, they cover
modification of the file, and distribution when not linked into a
combined executable.)
Libiberty 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
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with libiberty; see the file COPYING.LIB.
If not, see <http://www.gnu.org/licenses/>. */
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
#include "safe-ctype.h"
#include <sys/types.h>
#include <string.h>
#include <stdio.h>
#ifdef HAVE_STRING_H
#include <string.h>
#else
extern size_t strlen(const char *s);
extern int strncmp(const char *s1, const char *s2, size_t n);
extern void *memset(void *s, int c, size_t n);
#endif
#include <demangle.h>
#include "libiberty.h"
#include "rust-demangle.h"
/* Mangled Rust symbols look like this:
_$LT$std..sys..fd..FileDesc$u20$as$u20$core..ops..Drop$GT$::drop::hc68340e1baa4987a
The original symbol is:
<std::sys::fd::FileDesc as core::ops::Drop>::drop
The last component of the path is a 64-bit hash in lowercase hex,
prefixed with "h". Rust does not have a global namespace between
crates, an illusion which Rust maintains by using the hash to
distinguish things that would otherwise have the same symbol.
Any path component not starting with a XID_Start character is
prefixed with "_".
The following escape sequences are used:
"," => $C$
"@" => $SP$
"*" => $BP$
"&" => $RF$
"<" => $LT$
">" => $GT$
"(" => $LP$
")" => $RP$
" " => $u20$
"\"" => $u22$
"'" => $u27$
"+" => $u2b$
";" => $u3b$
"[" => $u5b$
"]" => $u5d$
"{" => $u7b$
"}" => $u7d$
"~" => $u7e$
A double ".." means "::" and a single "." means "-".
The only characters allowed in the mangled symbol are a-zA-Z0-9 and _.:$ */
static const char *hash_prefix = "::h";
static const size_t hash_prefix_len = 3;
static const size_t hash_len = 16;
static int is_prefixed_hash (const char *start);
static int looks_like_rust (const char *sym, size_t len);
static int unescape (const char **in, char **out, const char *seq, char value);
/* INPUT: sym: symbol that has been through C++ (gnu v3) demangling
This function looks for the following indicators:
1. The hash must consist of "h" followed by 16 lowercase hex digits.
2. As a sanity check, the hash must use between 5 and 15 of the 16
possible hex digits. This is true of 99.9998% of hashes so once
in your life you may see a false negative. The point is to
notice path components that could be Rust hashes but are
probably not, like "haaaaaaaaaaaaaaaa". In this case a false
positive (non-Rust symbol has an important path component
removed because it looks like a Rust hash) is worse than a false
negative (the rare Rust symbol is not demangled) so this sets
the balance in favor of false negatives.
3. There must be no characters other than a-zA-Z0-9 and _.:$
4. There must be no unrecognized $-sign sequences.
5. There must be no sequence of three or more dots in a row ("..."). */
int
rust_is_mangled (const char *sym)
{
size_t len, len_without_hash;
if (!sym)
return 0;
len = strlen (sym);
if (len <= hash_prefix_len + hash_len)
/* Not long enough to contain "::h" + hash + something else */
return 0;
len_without_hash = len - (hash_prefix_len + hash_len);
if (!is_prefixed_hash (sym + len_without_hash))
return 0;
return looks_like_rust (sym, len_without_hash);
}
/* A hash is the prefix "::h" followed by 16 lowercase hex digits. The
hex digits must comprise between 5 and 15 (inclusive) distinct
digits. */
static int
is_prefixed_hash (const char *str)
{
const char *end;
char seen[16];
size_t i;
int count;
if (strncmp (str, hash_prefix, hash_prefix_len))
return 0;
str += hash_prefix_len;
memset (seen, 0, sizeof(seen));
for (end = str + hash_len; str < end; str++)
if (*str >= '0' && *str <= '9')
seen[*str - '0'] = 1;
else if (*str >= 'a' && *str <= 'f')
seen[*str - 'a' + 10] = 1;
else
return 0;
/* Count how many distinct digits seen */
count = 0;
for (i = 0; i < 16; i++)
if (seen[i])
count++;
return count >= 5 && count <= 15;
}
static int
looks_like_rust (const char *str, size_t len)
{
const char *end = str + len;
while (str < end)
switch (*str)
{
case '$':
if (!strncmp (str, "$C$", 3))
str += 3;
else if (!strncmp (str, "$SP$", 4)
|| !strncmp (str, "$BP$", 4)
|| !strncmp (str, "$RF$", 4)
|| !strncmp (str, "$LT$", 4)
|| !strncmp (str, "$GT$", 4)
|| !strncmp (str, "$LP$", 4)
|| !strncmp (str, "$RP$", 4))
str += 4;
else if (!strncmp (str, "$u20$", 5)
|| !strncmp (str, "$u22$", 5)
|| !strncmp (str, "$u27$", 5)
|| !strncmp (str, "$u2b$", 5)
|| !strncmp (str, "$u3b$", 5)
|| !strncmp (str, "$u5b$", 5)
|| !strncmp (str, "$u5d$", 5)
|| !strncmp (str, "$u7b$", 5)
|| !strncmp (str, "$u7d$", 5)
|| !strncmp (str, "$u7e$", 5))
str += 5;
else
return 0;
break;
case '.':
/* Do not allow three or more consecutive dots */
if (!strncmp (str, "...", 3))
return 0;
/* Fall through */
case 'a': case 'b': case 'c': case 'd': case 'e': case 'f':
case 'g': case 'h': case 'i': case 'j': case 'k': case 'l':
case 'm': case 'n': case 'o': case 'p': case 'q': case 'r':
case 's': case 't': case 'u': case 'v': case 'w': case 'x':
case 'y': case 'z':
case 'A': case 'B': case 'C': case 'D': case 'E': case 'F':
case 'G': case 'H': case 'I': case 'J': case 'K': case 'L':
case 'M': case 'N': case 'O': case 'P': case 'Q': case 'R':
case 'S': case 'T': case 'U': case 'V': case 'W': case 'X':
case 'Y': case 'Z':
case '0': case '1': case '2': case '3': case '4': case '5':
case '6': case '7': case '8': case '9':
case '_':
case ':':
str++;
break;
default:
return 0;
}
return 1;
}
/*
INPUT: sym: symbol for which rust_is_mangled(sym) returned 1.
The input is demangled in-place because the mangled name is always
longer than the demangled one. */
void
rust_demangle_sym (char *sym)
{
const char *in;
char *out;
const char *end;
if (!sym)
return;
in = sym;
out = sym;
end = sym + strlen (sym) - (hash_prefix_len + hash_len);
while (in < end)
switch (*in)
{
case '$':
if (!(unescape (&in, &out, "$C$", ',')
|| unescape (&in, &out, "$SP$", '@')
|| unescape (&in, &out, "$BP$", '*')
|| unescape (&in, &out, "$RF$", '&')
|| unescape (&in, &out, "$LT$", '<')
|| unescape (&in, &out, "$GT$", '>')
|| unescape (&in, &out, "$LP$", '(')
|| unescape (&in, &out, "$RP$", ')')
|| unescape (&in, &out, "$u20$", ' ')
|| unescape (&in, &out, "$u22$", '\"')
|| unescape (&in, &out, "$u27$", '\'')
|| unescape (&in, &out, "$u2b$", '+')
|| unescape (&in, &out, "$u3b$", ';')
|| unescape (&in, &out, "$u5b$", '[')
|| unescape (&in, &out, "$u5d$", ']')
|| unescape (&in, &out, "$u7b$", '{')
|| unescape (&in, &out, "$u7d$", '}')
|| unescape (&in, &out, "$u7e$", '~'))) {
/* unexpected escape sequence, not looks_like_rust. */
goto fail;
}
break;
case '_':
/* If this is the start of a path component and the next
character is an escape sequence, ignore the underscore. The
mangler inserts an underscore to make sure the path
component begins with a XID_Start character. */
if ((in == sym || in[-1] == ':') && in[1] == '$')
in++;
else
*out++ = *in++;
break;
case '.':
if (in[1] == '.')
{
/* ".." becomes "::" */
*out++ = ':';
*out++ = ':';
in += 2;
}
else
{
/* "." becomes "-" */
*out++ = '-';
in++;
}
break;
case 'a': case 'b': case 'c': case 'd': case 'e': case 'f':
case 'g': case 'h': case 'i': case 'j': case 'k': case 'l':
case 'm': case 'n': case 'o': case 'p': case 'q': case 'r':
case 's': case 't': case 'u': case 'v': case 'w': case 'x':
case 'y': case 'z':
case 'A': case 'B': case 'C': case 'D': case 'E': case 'F':
case 'G': case 'H': case 'I': case 'J': case 'K': case 'L':
case 'M': case 'N': case 'O': case 'P': case 'Q': case 'R':
case 'S': case 'T': case 'U': case 'V': case 'W': case 'X':
case 'Y': case 'Z':
case '0': case '1': case '2': case '3': case '4': case '5':
case '6': case '7': case '8': case '9':
case ':':
*out++ = *in++;
break;
default:
/* unexpected character in symbol, not looks_like_rust. */
goto fail;
}
goto done;
fail:
*out++ = '?'; /* This is pretty lame, but it's hard to do better. */
done:
*out = '\0';
}
static int
unescape (const char **in, char **out, const char *seq, char value)
{
size_t len = strlen (seq);
if (strncmp (*in, seq, len))
return 0;
**out = value;
*in += len;
*out += 1;
return 1;
}

View file

@ -1,11 +1,10 @@
/* ###
* IP: LGPL 2.1
* REVIEWED: YES
* NOTE: See binutils/include/COPYING
*/
/* <ctype.h> replacement macros.
Copyright (C) 2000, 2001, 2002, 2003, 2004,
2005 Free Software Foundation, Inc.
Copyright (C) 2000-2019 Free Software Foundation, Inc.
Contributed by Zack Weinberg <zackw@stanford.edu>.
This file is part of the libiberty library.

View file

@ -1,9 +1,9 @@
/* ###
* IP: LGPL 2.1
* REVIEWED: YES
* NOTE: See binutils/libiberty/COPYING.LIB
*/
/* xexit.c -- Run any exit handlers, then exit.
Copyright (C) 1994, 95, 1997 Free Software Foundation, Inc.
Copyright (C) 1994-2019 Free Software Foundation, Inc.
This file is part of the libiberty library.
Libiberty is free software; you can redistribute it and/or

View file

@ -1,7 +1,5 @@
/* ###
* IP: LGPL 2.1
* REVIEWED: YES
* NOTE: license is not in file, but in the directory from whence it came: binutils-2.24/libiberty/COPYING.LIB
* IP: Public Domain
*/
/* xstrdup.c -- Duplicate a string in memory, using xmalloc.
This trivial function is in the public domain.

View file

@ -1,11 +1,9 @@
/* ###
* IP: GPL 3
* REVIEWED: YES
* IP: LGPL 2.1
* NOTE: See binutils/include/COPYING
*/
/* ANSI and traditional C compatability macros
Copyright 1991, 1992, 1993, 1994, 1995, 1996, 1998, 1999, 2000, 2001,
2002, 2003, 2004, 2005, 2006, 2007, 2009, 2010
Free Software Foundation, Inc.
Copyright (C) 1991-2019 Free Software Foundation, Inc.
This file is part of the GNU C Library.
This program is free software; you can redistribute it and/or modify
@ -28,93 +26,16 @@ Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA.
Macro ANSI C definition Traditional C definition
----- ---- - ---------- ----------- - ----------
ANSI_PROTOTYPES 1 not defined
PTR `void *' `char *'
PTRCONST `void *const' `char *'
LONG_DOUBLE `long double' `double'
const not defined `'
volatile not defined `'
signed not defined `'
VA_START(ap, var) va_start(ap, var) va_start(ap)
Note that it is safe to write "void foo();" indicating a function
with no return value, in all K+R compilers we have been able to test.
For declaring functions with prototypes, we also provide these:
PARAMS ((prototype))
-- for functions which take a fixed number of arguments. Use this
when declaring the function. When defining the function, write a
K+R style argument list. For example:
char *strcpy PARAMS ((char *dest, char *source));
...
char *
strcpy (dest, source)
char *dest;
char *source;
{ ... }
VPARAMS ((prototype, ...))
-- for functions which take a variable number of arguments. Use
PARAMS to declare the function, VPARAMS to define it. For example:
int printf PARAMS ((const char *format, ...));
...
int
printf VPARAMS ((const char *format, ...))
{
...
}
For writing functions which take variable numbers of arguments, we
also provide the VA_OPEN, VA_CLOSE, and VA_FIXEDARG macros. These
hide the differences between K+R <varargs.h> and C89 <stdarg.h> more
thoroughly than the simple VA_START() macro mentioned above.
VA_OPEN and VA_CLOSE are used *instead of* va_start and va_end.
Immediately after VA_OPEN, put a sequence of VA_FIXEDARG calls
corresponding to the list of fixed arguments. Then use va_arg
normally to get the variable arguments, or pass your va_list object
around. You do not declare the va_list yourself; VA_OPEN does it
for you.
Here is a complete example:
int
printf VPARAMS ((const char *format, ...))
{
int result;
VA_OPEN (ap, format);
VA_FIXEDARG (ap, const char *, format);
result = vfprintf (stdout, format, ap);
VA_CLOSE (ap);
return result;
}
You can declare variables either before or after the VA_OPEN,
VA_FIXEDARG sequence. Also, VA_OPEN and VA_CLOSE are the beginning
and end of a block. They must appear at the same nesting level,
and any variables declared after VA_OPEN go out of scope at
VA_CLOSE. Unfortunately, with a K+R compiler, that includes the
argument list. You can have multiple instances of VA_OPEN/VA_CLOSE
pairs in a single function in case you need to traverse the
argument list more than once.
For ease of writing code which uses GCC extensions but needs to be
portable to other compilers, we provide the GCC_VERSION macro that
simplifies testing __GNUC__ and __GNUC_MINOR__ together, and various
wrappers around __attribute__. Also, __extension__ will be #defined
to nothing if it doesn't work. See below.
This header also defines a lot of obsolete macros:
CONST, VOLATILE, SIGNED, PROTO, EXFUN, DEFUN, DEFUN_VOID,
AND, DOTS, NOARGS. Don't use them. */
to nothing if it doesn't work. See below. */
#ifndef _ANSIDECL_H
#define _ANSIDECL_H 1
@ -153,28 +74,8 @@ So instead we use the macro below and test it against specific values. */
C++ compilers, does not define __STDC__, though it acts as if this
was so. (Verified versions: 5.7, 6.2, 6.3, 6.5) */
#define ANSI_PROTOTYPES 1
#define PTR void *
#define PTRCONST void *const
#define LONG_DOUBLE long double
/* PARAMS is often defined elsewhere (e.g. by libintl.h), so wrap it in
a #ifndef. */
#ifndef PARAMS
#define PARAMS(ARGS) ARGS
#endif
#define VPARAMS(ARGS) ARGS
#define VA_START(VA_LIST, VAR) va_start(VA_LIST, VAR)
/* variadic function helper macros */
/* "struct Qdmy" swallows the semicolon after VA_OPEN/VA_FIXEDARG's
use without inhibiting further decls and without declaring an
actual variable. */
#define VA_OPEN(AP, VAR) { va_list AP; va_start(AP, VAR); { struct Qdmy
#define VA_CLOSE(AP) } va_end(AP); }
#define VA_FIXEDARG(AP, T, N) struct Qdmy
#undef const
#undef volatile
#undef signed
@ -192,35 +93,9 @@ So instead we use the macro below and test it against specific values. */
# endif
#endif
/* These are obsolete. Do not use. */
#ifndef IN_GCC
#define CONST const
#define VOLATILE volatile
#define SIGNED signed
#define PROTO(type, name, arglist) type name arglist
#define EXFUN(name, proto) name proto
#define DEFUN(name, arglist, args) name(args)
#define DEFUN_VOID(name) name(void)
#define AND ,
#define DOTS , ...
#define NOARGS void
#endif /* ! IN_GCC */
#else /* Not ANSI C. */
#undef ANSI_PROTOTYPES
#define PTR char *
#define PTRCONST PTR
#define LONG_DOUBLE double
#define PARAMS(args) ()
#define VPARAMS(args) (va_alist) va_dcl
#define VA_START(va_list, var) va_start(va_list)
#define VA_OPEN(AP, VAR) { va_list AP; va_start(AP); { struct Qdmy
#define VA_CLOSE(AP) } va_end(AP); }
#define VA_FIXEDARG(AP, TYPE, NAME) TYPE NAME = va_arg(AP, TYPE)
/* some systems define these in header files for non-ansi mode */
#undef const
@ -232,20 +107,6 @@ So instead we use the macro below and test it against specific values. */
#define signed
#define inline
#ifndef IN_GCC
#define CONST
#define VOLATILE
#define SIGNED
#define PROTO(type, name, arglist) type name ()
#define EXFUN(name, proto) name()
#define DEFUN(name, arglist, args) name arglist args;
#define DEFUN_VOID(name) name()
#define AND ;
#define DOTS
#define NOARGS
#endif /* ! IN_GCC */
#endif /* ANSI C. */
/* Define macros for some gcc attributes. This permits us to use the
@ -315,6 +176,15 @@ So instead we use the macro below and test it against specific values. */
# endif /* GNUC >= 3.3 */
#endif /* ATTRIBUTE_NONNULL */
/* Attribute `returns_nonnull' was valid as of gcc 4.9. */
#ifndef ATTRIBUTE_RETURNS_NONNULL
# if (GCC_VERSION >= 4009)
# define ATTRIBUTE_RETURNS_NONNULL __attribute__ ((__returns_nonnull__))
# else
# define ATTRIBUTE_RETURNS_NONNULL
# endif /* GNUC >= 4.9 */
#endif /* ATTRIBUTE_RETURNS_NONNULL */
/* Attribute `pure' was valid as of gcc 3.0. */
#ifndef ATTRIBUTE_PURE
# if (GCC_VERSION >= 3000)
@ -386,7 +256,7 @@ So instead we use the macro below and test it against specific values. */
# endif /* GNUC >= 3.0 */
#endif /* ATTRIBUTE_ALIGNED_ALIGNOF */
/* Useful for structures whose layout must much some binary specification
/* Useful for structures whose layout must match some binary specification
regardless of the alignment and padding qualities of the compiler. */
#ifndef ATTRIBUTE_PACKED
# define ATTRIBUTE_PACKED __attribute__ ((packed))
@ -408,6 +278,24 @@ So instead we use the macro below and test it against specific values. */
# endif /* GNUC >= 4.3 */
#endif /* ATTRIBUTE_HOT */
/* Attribute 'no_sanitize_undefined' was valid as of gcc 4.9. */
#ifndef ATTRIBUTE_NO_SANITIZE_UNDEFINED
# if (GCC_VERSION >= 4009)
# define ATTRIBUTE_NO_SANITIZE_UNDEFINED __attribute__ ((no_sanitize_undefined))
# else
# define ATTRIBUTE_NO_SANITIZE_UNDEFINED
# endif /* GNUC >= 4.9 */
#endif /* ATTRIBUTE_NO_SANITIZE_UNDEFINED */
/* Attribute 'nonstring' was valid as of gcc 8. */
#ifndef ATTRIBUTE_NONSTRING
# if GCC_VERSION >= 8000
# define ATTRIBUTE_NONSTRING __attribute__ ((__nonstring__))
# else
# define ATTRIBUTE_NONSTRING
# endif
#endif
/* We use __extension__ in some places to suppress -pedantic warnings
about GCC extensions. This feature didn't work properly before
gcc 2.8. */
@ -438,6 +326,79 @@ So instead we use the macro below and test it against specific values. */
#define ENUM_BITFIELD(TYPE) unsigned int
#endif
#if __cpp_constexpr >= 200704
#define CONSTEXPR constexpr
#else
#define CONSTEXPR
#endif
/* C++11 adds the ability to add "override" after an implementation of a
virtual function in a subclass, to:
(A) document that this is an override of a virtual function
(B) allow the compiler to issue a warning if it isn't (e.g. a mismatch
of the type signature).
Similarly, it allows us to add a "final" to indicate that no subclass
may subsequently override the vfunc.
Provide OVERRIDE and FINAL as macros, allowing us to get these benefits
when compiling with C++11 support, but without requiring C++11.
For gcc, use "-std=c++11" to enable C++11 support; gcc 6 onwards enables
this by default (actually GNU++14). */
#if defined __cplusplus
# if __cplusplus >= 201103
/* C++11 claims to be available: use it. Final/override were only
implemented in 4.7, though. */
# if GCC_VERSION < 4007
# define OVERRIDE
# define FINAL
# else
# define OVERRIDE override
# define FINAL final
# endif
# elif GCC_VERSION >= 4007
/* G++ 4.7 supports __final in C++98. */
# define OVERRIDE
# define FINAL __final
# else
/* No C++11 support; leave the macros empty. */
# define OVERRIDE
# define FINAL
# endif
#else
/* No C++11 support; leave the macros empty. */
# define OVERRIDE
# define FINAL
#endif
/* A macro to disable the copy constructor and assignment operator.
When building with C++11 and above, the methods are explicitly
deleted, causing a compile-time error if something tries to copy.
For C++03, this just declares the methods, causing a link-time
error if the methods end up called (assuming you don't
define them). For C++03, for best results, place the macro
under the private: access specifier, like this,
class name_lookup
{
private:
DISABLE_COPY_AND_ASSIGN (name_lookup);
};
so that most attempts at copy are caught at compile-time. */
#if __cplusplus >= 201103
#define DISABLE_COPY_AND_ASSIGN(TYPE) \
TYPE (const TYPE&) = delete; \
void operator= (const TYPE &) = delete
#else
#define DISABLE_COPY_AND_ASSIGN(TYPE) \
TYPE (const TYPE&); \
void operator= (const TYPE &)
#endif /* __cplusplus >= 201103 */
#ifdef __cplusplus
}
#endif

View file

@ -1,9 +1,9 @@
/* ###
* IP: GPL 3 Linking Permitted
* NOTE: See binutils/libiberty/COPYING.LIB; Used GPL 3 from this file's header
*/
/* Internal demangler interface for g++ V3 ABI.
Copyright (C) 2003, 2004, 2005, 2006, 2007, 2010
Free Software Foundation, Inc.
Copyright (C) 2003-2019 Free Software Foundation, Inc.
Written by Ian Lance Taylor <ian@wasabisystems.com>.
This file is part of the libiberty library, which is part of GCC.
@ -115,16 +115,20 @@ struct d_info
int next_sub;
/* The number of available entries in the subs array. */
int num_subs;
/* The number of substitutions which we actually made from the subs
array, plus the number of template parameter references we
saw. */
int did_subs;
/* The last name we saw, for constructors and destructors. */
struct demangle_component *last_name;
/* A running total of the length of large expansions from the
mangled name to the demangled name, such as standard
substitutions and builtin types. */
int expansion;
/* Non-zero if we are parsing an expression. */
int is_expression;
/* Non-zero if we are parsing the type operand of a conversion
operator, but not when in an expression. */
int is_conversion;
/* If DMGL_NO_RECURSE_LIMIT is not active then this is set to
the current recursion level. */
unsigned int recursion_level;
};
/* To avoid running past the ending '\0', don't:
@ -133,12 +137,37 @@ struct d_info
- call d_check_char(di, '\0')
Everything else is safe. */
#define d_peek_char(di) (*((di)->n))
#define d_peek_next_char(di) ((di)->n[1])
#define d_advance(di, i) ((di)->n += (i))
#ifndef CHECK_DEMANGLER
# define d_peek_next_char(di) ((di)->n[1])
# define d_advance(di, i) ((di)->n += (i))
#endif
#define d_check_char(di, c) (d_peek_char(di) == c ? ((di)->n++, 1) : 0)
#define d_next_char(di) (d_peek_char(di) == '\0' ? '\0' : *((di)->n++))
#define d_str(di) ((di)->n)
#ifdef CHECK_DEMANGLER
static inline char
d_peek_next_char (const struct d_info *di)
{
if (!di->n[0])
abort ();
return di->n[1];
}
static inline void
d_advance (struct d_info *di, int i)
{
if (i < 0)
abort ();
while (i--)
{
if (!di->n[0])
abort ();
di->n++;
}
}
#endif
/* Functions and arrays in cp-demangle.c which are referenced by
functions in cp-demint.c. */
#ifdef IN_GLIBCPP_V3

View file

@ -1,11 +1,10 @@
/* ###
* IP: LGPL 3.0
* REVIEWED: YES
* IP: LGPL 2.1
* NOTE: See binutils/include/COPYING
*/
/* Defs for interface to demanglers.
Copyright 1992, 1993, 1994, 1995, 1996, 1997, 1998, 2000, 2001, 2002,
2003, 2004, 2005, 2007, 2008, 2009, 2010 Free Software Foundation, Inc.
Copyright (C) 1992-2019 Free Software Foundation, Inc.
This program is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public License
as published by the Free Software Foundation; either version 2, or
@ -58,19 +57,25 @@ extern "C" {
*/
#define DMGL_AUTO (1 << 8)
#define DMGL_GNU (1 << 9)
#define DMGL_LUCID (1 << 10)
#define DMGL_ARM (1 << 11)
#define DMGL_HP (1 << 12) /* For the HP aCC compiler;
same as ARM except for
template arguments, etc. */
#define DMGL_EDG (1 << 13)
#define DMGL_GNU_V3 (1 << 14)
#define DMGL_GNAT (1 << 15)
#define DMGL_DLANG (1 << 16)
#define DMGL_RUST (1 << 17) /* Rust wraps GNU_V3 style mangling. */
/* If none of these are set, use 'current_demangling_style' as the default. */
#define DMGL_STYLE_MASK (DMGL_AUTO|DMGL_GNU|DMGL_LUCID|DMGL_ARM|DMGL_HP|DMGL_EDG|DMGL_GNU_V3|DMGL_JAVA|DMGL_GNAT)
#define DMGL_STYLE_MASK (DMGL_AUTO|DMGL_GNU_V3|DMGL_JAVA|DMGL_GNAT|DMGL_DLANG|DMGL_RUST)
/* Disable a limit on the depth of recursion in mangled strings.
Note if this limit is disabled then stack exhaustion is possible when
demangling pathologically complicated strings. Bug reports about stack
exhaustion when the option is enabled will be rejected. */
#define DMGL_NO_RECURSE_LIMIT (1 << 18)
/* If DMGL_NO_RECURSE_LIMIT is not enabled, then this is the value used as
the maximum depth of recursion allowed. It should be enough for any
real-world mangled name. */
#define DEMANGLE_RECURSION_LIMIT 2048
/* Enumeration of possible demangling styles.
Lucid and ARM styles are still kept logically distinct, even though
@ -84,41 +89,32 @@ extern enum demangling_styles
no_demangling = -1,
unknown_demangling = 0,
auto_demangling = DMGL_AUTO,
gnu_demangling = DMGL_GNU,
lucid_demangling = DMGL_LUCID,
arm_demangling = DMGL_ARM,
hp_demangling = DMGL_HP,
edg_demangling = DMGL_EDG,
gnu_v3_demangling = DMGL_GNU_V3,
java_demangling = DMGL_JAVA,
gnat_demangling = DMGL_GNAT
gnat_demangling = DMGL_GNAT,
dlang_demangling = DMGL_DLANG,
rust_demangling = DMGL_RUST
} current_demangling_style;
/* Define string names for the various demangling styles. */
#define NO_DEMANGLING_STYLE_STRING "none"
#define AUTO_DEMANGLING_STYLE_STRING "auto"
#define GNU_DEMANGLING_STYLE_STRING "gnu"
#define LUCID_DEMANGLING_STYLE_STRING "lucid"
#define ARM_DEMANGLING_STYLE_STRING "arm"
#define HP_DEMANGLING_STYLE_STRING "hp"
#define EDG_DEMANGLING_STYLE_STRING "edg"
#define GNU_V3_DEMANGLING_STYLE_STRING "gnu-v3"
#define JAVA_DEMANGLING_STYLE_STRING "java"
#define GNAT_DEMANGLING_STYLE_STRING "gnat"
#define DLANG_DEMANGLING_STYLE_STRING "dlang"
#define RUST_DEMANGLING_STYLE_STRING "rust"
/* Some macros to test what demangling style is active. */
#define CURRENT_DEMANGLING_STYLE current_demangling_style
#define AUTO_DEMANGLING (((int) CURRENT_DEMANGLING_STYLE) & DMGL_AUTO)
#define GNU_DEMANGLING (((int) CURRENT_DEMANGLING_STYLE) & DMGL_GNU)
#define LUCID_DEMANGLING (((int) CURRENT_DEMANGLING_STYLE) & DMGL_LUCID)
#define ARM_DEMANGLING (((int) CURRENT_DEMANGLING_STYLE) & DMGL_ARM)
#define HP_DEMANGLING (((int) CURRENT_DEMANGLING_STYLE) & DMGL_HP)
#define EDG_DEMANGLING (((int) CURRENT_DEMANGLING_STYLE) & DMGL_EDG)
#define GNU_V3_DEMANGLING (((int) CURRENT_DEMANGLING_STYLE) & DMGL_GNU_V3)
#define JAVA_DEMANGLING (((int) CURRENT_DEMANGLING_STYLE) & DMGL_JAVA)
#define GNAT_DEMANGLING (((int) CURRENT_DEMANGLING_STYLE) & DMGL_GNAT)
#define DLANG_DEMANGLING (((int) CURRENT_DEMANGLING_STYLE) & DMGL_DLANG)
#define RUST_DEMANGLING (((int) CURRENT_DEMANGLING_STYLE) & DMGL_RUST)
/* Provide information about the available demangle styles. This code is
pulled from gdb into libiberty because it is useful to binutils also. */
@ -133,21 +129,12 @@ extern const struct demangler_engine
extern char *
cplus_demangle (const char *mangled, int options);
extern int
cplus_demangle_opname (const char *opname, char *result, int options);
extern const char *
cplus_mangle_opname (const char *opname, int options);
/* Note: This sets global state. FIXME if you care about multi-threading. */
extern void
set_cplus_marker_for_demangling (int ch);
extern enum demangling_styles
extern enum demangling_styles
cplus_demangle_set_style (enum demangling_styles style);
extern enum demangling_styles
extern enum demangling_styles
cplus_demangle_name_to_style (const char *name);
/* Callback typedef for allocation-less demangler interfaces. */
@ -173,10 +160,38 @@ java_demangle_v3 (const char *mangled);
char *
ada_demangle (const char *mangled, int options);
extern char *
dlang_demangle (const char *mangled, int options);
/* Returns non-zero iff MANGLED is a rust mangled symbol. MANGLED must
already have been demangled through cplus_demangle_v3. If this function
returns non-zero then MANGLED can be demangled (in-place) using
RUST_DEMANGLE_SYM. */
extern int
rust_is_mangled (const char *mangled);
/* Demangles SYM (in-place) if RUST_IS_MANGLED returned non-zero for SYM.
If RUST_IS_MANGLED returned zero for SYM then RUST_DEMANGLE_SYM might
replace characters that cannot be demangled with '?' and might truncate
SYM. After calling RUST_DEMANGLE_SYM SYM might be shorter, but never
larger. */
extern void
rust_demangle_sym (char *sym);
/* Demangles MANGLED if it was GNU_V3 and then RUST mangled, otherwise
returns NULL. Uses CPLUS_DEMANGLE_V3, RUST_IS_MANGLED and
RUST_DEMANGLE_SYM. Returns a new string that is owned by the caller. */
extern char *
rust_demangle (const char *mangled, int options);
enum gnu_v3_ctor_kinds {
gnu_v3_complete_object_ctor = 1,
gnu_v3_base_object_ctor,
gnu_v3_complete_object_allocating_ctor,
/* These are not part of the V3 ABI. Unified constructors are generated
as a speed-for-space optimization when the -fdeclone-ctor-dtor option
is used, and are always internal symbols. */
gnu_v3_unified_ctor,
gnu_v3_object_ctor_group
};
@ -192,6 +207,10 @@ enum gnu_v3_dtor_kinds {
gnu_v3_deleting_dtor = 1,
gnu_v3_complete_object_dtor,
gnu_v3_base_object_dtor,
/* These are not part of the V3 ABI. Unified destructors are generated
as a speed-for-space optimization when the -fdeclone-ctor-dtor option
is used, and are always internal symbols. */
gnu_v3_unified_dtor,
gnu_v3_object_dtor_group
};
@ -357,6 +376,9 @@ enum demangle_component_type
template argument, and the right subtree is either NULL or
another TEMPLATE_ARGLIST node. */
DEMANGLE_COMPONENT_TEMPLATE_ARGLIST,
/* A template parameter object (C++20). The left subtree is the
corresponding template argument. */
DEMANGLE_COMPONENT_TPARM_OBJ,
/* An initializer list. The left subtree is either an explicit type or
NULL, and the right subtree is a DEMANGLE_COMPONENT_ARGLIST. */
DEMANGLE_COMPONENT_INITIALIZER_LIST,
@ -369,6 +391,10 @@ enum demangle_component_type
/* A typecast, represented as a unary operator. The one subtree is
the type to which the argument should be cast. */
DEMANGLE_COMPONENT_CAST,
/* A conversion operator, represented as a unary operator. The one
subtree is the type to which the argument should be converted
to. */
DEMANGLE_COMPONENT_CONVERSION,
/* A nullary expression. The left subtree is the operator. */
DEMANGLE_COMPONENT_NULLARY,
/* A unary expression. The left subtree is the operator, and the
@ -432,8 +458,12 @@ enum demangle_component_type
DEMANGLE_COMPONENT_PACK_EXPANSION,
/* A name with an ABI tag. */
DEMANGLE_COMPONENT_TAGGED_NAME,
/* A transaction-safe function type. */
DEMANGLE_COMPONENT_TRANSACTION_SAFE,
/* A cloned function. */
DEMANGLE_COMPONENT_CLONE
DEMANGLE_COMPONENT_CLONE,
DEMANGLE_COMPONENT_NOEXCEPT,
DEMANGLE_COMPONENT_THROW_SPEC
};
/* Types which are only used internally. */
@ -451,6 +481,11 @@ struct demangle_component
/* The type of this component. */
enum demangle_component_type type;
/* Guard against recursive component printing.
Initialize to zero. Private to d_print_comp.
All other fields are final after initialization. */
int d_printing;
union
{
/* For DEMANGLE_COMPONENT_NAME. */
@ -645,7 +680,7 @@ cplus_demangle_v3_components (const char *mangled, int options, void **mem);
extern char *
cplus_demangle_print (int options,
const struct demangle_component *tree,
struct demangle_component *tree,
int estimated_length,
size_t *p_allocated_size);
@ -665,7 +700,7 @@ cplus_demangle_print (int options,
extern int
cplus_demangle_print_callback (int options,
const struct demangle_component *tree,
struct demangle_component *tree,
demangle_callbackref callback, void *opaque);
#ifdef __cplusplus

View file

@ -1,10 +1,9 @@
/* ###
* IP: GPL 3
* REVIEWED: YES
* NOTE: See binutils/include/COPYING3
*/
/* An abstract string datatype.
Copyright (C) 1998, 1999, 2000, 2002, 2004, 2005, 2009
Free Software Foundation, Inc.
Copyright (C) 1998-2019 Free Software Foundation, Inc.
Contributed by Mark Mitchell (mark@markmitchell.com).
This file is part of GCC.

View file

@ -1,10 +1,9 @@
/* ###
* IP: GPL 3
* REVIEWED: YES
* NOTE: See binutils/include/COPYING3
*/
/* Declarations for getopt.
Copyright 1989, 1990, 1991, 1992, 1993, 1994, 1996, 1997, 1998, 2000,
2002 Free Software Foundation, Inc.
Copyright (C) 1989-2019 Free Software Foundation, Inc.
NOTE: The canonical source of this file is maintained with the GNU C Library.
Bugs can be reported to bug-glibc@gnu.org.

View file

@ -1,11 +1,10 @@
/* ###
* IP: GPL 3
* REVIEWED: YES
* NOTE: See binutils/include/COPYING3
*/
/* Function declarations for libiberty.
Copyright 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005,
2006, 2007, 2008, 2009, 2010, 2011 Free Software Foundation, Inc.
Copyright (C) 1997-2019 Free Software Foundation, Inc.
Note - certain prototypes declared in this header file are for
functions whoes implementation copyright does not belong to the
@ -85,19 +84,19 @@ extern void freeargv (char **);
/* Duplicate an argument vector. Allocates memory using malloc. Use
freeargv to free the vector. */
extern char **dupargv (char **) ATTRIBUTE_MALLOC;
extern char **dupargv (char * const *) ATTRIBUTE_MALLOC;
/* Expand "@file" arguments in argv. */
extern void expandargv PARAMS ((int *, char ***));
extern void expandargv (int *, char ***);
/* Write argv to an @-file, inserting necessary quoting. */
extern int writeargv PARAMS ((char **, FILE *));
extern int writeargv (char * const *, FILE *);
/* Return the number of elements in argv. */
extern int countargv (char**);
extern int countargv (char * const *);
/* Return the last component of a path name. Note that we can't use a
prototype here because the parameter is declared inconsistently
@ -110,8 +109,11 @@ extern int countargv (char**);
to find the declaration so provide a fully prototyped one. If it
is 1, we found it so don't provide any declaration at all. */
#if !HAVE_DECL_BASENAME
#if defined (__GNU_LIBRARY__ ) || defined (__linux__) || defined (__FreeBSD__) || defined (__OpenBSD__) || defined(__NetBSD__) || defined (__CYGWIN__) || defined (__CYGWIN32__) || defined (__MINGW32__) || defined (HAVE_DECL_BASENAME)
extern char *basename (const char *);
#if defined (__GNU_LIBRARY__ ) || defined (__linux__) \
|| defined (__FreeBSD__) || defined (__OpenBSD__) || defined (__NetBSD__) \
|| defined (__CYGWIN__) || defined (__CYGWIN32__) || defined (__MINGW32__) \
|| defined (__DragonFly__) || defined (HAVE_DECL_BASENAME)
extern char *basename (const char *) ATTRIBUTE_RETURNS_NONNULL ATTRIBUTE_NONNULL(1);
#else
/* Do not allow basename to be used if there is no prototype seen. We
either need to use the above prototype or have one from
@ -122,18 +124,18 @@ extern char *basename (const char *);
/* A well-defined basename () that is always compiled in. */
extern const char *lbasename (const char *);
extern const char *lbasename (const char *) ATTRIBUTE_RETURNS_NONNULL ATTRIBUTE_NONNULL(1);
/* Same, but assumes DOS semantics (drive name, backslash is also a
dir separator) regardless of host. */
extern const char *dos_lbasename (const char *);
extern const char *dos_lbasename (const char *) ATTRIBUTE_RETURNS_NONNULL ATTRIBUTE_NONNULL(1);
/* Same, but assumes Unix semantics (absolute paths always start with
a slash, only forward slash is accepted as dir separator)
regardless of host. */
extern const char *unix_lbasename (const char *);
extern const char *unix_lbasename (const char *) ATTRIBUTE_RETURNS_NONNULL ATTRIBUTE_NONNULL(1);
/* A well-defined realpath () that is always compiled in. */
@ -143,7 +145,7 @@ extern char *lrealpath (const char *);
the last argument of this function, to terminate the list of
strings. Allocates memory using xmalloc. */
extern char *concat (const char *, ...) ATTRIBUTE_MALLOC ATTRIBUTE_SENTINEL;
extern char *concat (const char *, ...) ATTRIBUTE_MALLOC ATTRIBUTE_RETURNS_NONNULL ATTRIBUTE_SENTINEL;
/* Concatenate an arbitrary number of strings. You must pass NULL as
the last argument of this function, to terminate the list of
@ -152,7 +154,7 @@ extern char *concat (const char *, ...) ATTRIBUTE_MALLOC ATTRIBUTE_SENTINEL;
pointer to be freed after the new string is created, similar to the
way xrealloc works. */
extern char *reconcat (char *, const char *, ...) ATTRIBUTE_MALLOC ATTRIBUTE_SENTINEL;
extern char *reconcat (char *, const char *, ...) ATTRIBUTE_MALLOC ATTRIBUTE_RETURNS_NONNULL ATTRIBUTE_SENTINEL;
/* Determine the length of concatenating an arbitrary number of
strings. You must pass NULL as the last argument of this function,
@ -165,14 +167,14 @@ extern unsigned long concat_length (const char *, ...) ATTRIBUTE_SENTINEL;
to terminate the list of strings. The supplied memory is assumed
to be large enough. */
extern char *concat_copy (char *, const char *, ...) ATTRIBUTE_SENTINEL;
extern char *concat_copy (char *, const char *, ...) ATTRIBUTE_RETURNS_NONNULL ATTRIBUTE_NONNULL(1) ATTRIBUTE_SENTINEL;
/* Concatenate an arbitrary number of strings into a GLOBAL area of
memory. You must pass NULL as the last argument of this function,
to terminate the list of strings. The supplied memory is assumed
to be large enough. */
extern char *concat_copy2 (const char *, ...) ATTRIBUTE_SENTINEL;
extern char *concat_copy2 (const char *, ...) ATTRIBUTE_RETURNS_NONNULL ATTRIBUTE_SENTINEL;
/* This is the global area used by concat_copy2. */
@ -228,14 +230,24 @@ extern char *make_relative_prefix (const char *, const char *,
extern char *make_relative_prefix_ignore_links (const char *, const char *,
const char *) ATTRIBUTE_MALLOC;
/* Returns a pointer to a directory path suitable for creating temporary
files in. */
extern const char *choose_tmpdir (void) ATTRIBUTE_RETURNS_NONNULL;
/* Choose a temporary directory to use for scratch files. */
extern char *choose_temp_base (void) ATTRIBUTE_MALLOC;
extern char *choose_temp_base (void) ATTRIBUTE_MALLOC ATTRIBUTE_RETURNS_NONNULL;
/* Return a temporary file name or NULL if unable to create one. */
extern char *make_temp_file (const char *) ATTRIBUTE_MALLOC;
/* Return a temporary file name with given PREFIX and SUFFIX
or NULL if unable to create one. */
extern char *make_temp_file_with_prefix (const char *, const char *) ATTRIBUTE_MALLOC;
/* Remove a link to a file unless it is special. */
extern int unlink_if_ordinary (const char *);
@ -260,7 +272,7 @@ extern int strtoerrno (const char *);
/* ANSI's strerror(), but more robust. */
extern char *xstrerror (int);
extern char *xstrerror (int) ATTRIBUTE_RETURNS_NONNULL;
/* Return the maximum signal number for which strsignal will return a
string. */
@ -302,30 +314,30 @@ extern void xmalloc_failed (size_t) ATTRIBUTE_NORETURN;
message to stderr (using the name set by xmalloc_set_program_name,
if any) and then call xexit. */
extern void *xmalloc (size_t) ATTRIBUTE_MALLOC;
extern void *xmalloc (size_t) ATTRIBUTE_MALLOC ATTRIBUTE_RETURNS_NONNULL;
/* Reallocate memory without fail. This works like xmalloc. Note,
realloc type functions are not suitable for attribute malloc since
they may return the same address across multiple calls. */
extern void *xrealloc (void *, size_t);
extern void *xrealloc (void *, size_t) ATTRIBUTE_RETURNS_NONNULL;
/* Allocate memory without fail and set it to zero. This works like
xmalloc. */
extern void *xcalloc (size_t, size_t) ATTRIBUTE_MALLOC;
extern void *xcalloc (size_t, size_t) ATTRIBUTE_MALLOC ATTRIBUTE_RETURNS_NONNULL;
/* Copy a string into a memory buffer without fail. */
extern char *xstrdup (const char *) ATTRIBUTE_MALLOC;
extern char *xstrdup (const char *) ATTRIBUTE_MALLOC ATTRIBUTE_RETURNS_NONNULL;
/* Copy at most N characters from string into a buffer without fail. */
extern char *xstrndup (const char *, size_t) ATTRIBUTE_MALLOC;
extern char *xstrndup (const char *, size_t) ATTRIBUTE_MALLOC ATTRIBUTE_RETURNS_NONNULL;
/* Copy an existing memory buffer to a new memory buffer without fail. */
extern void *xmemdup (const void *, size_t, size_t) ATTRIBUTE_MALLOC;
extern void *xmemdup (const void *, size_t, size_t) ATTRIBUTE_MALLOC ATTRIBUTE_RETURNS_NONNULL;
/* Physical memory routines. Return values are in BYTES. */
extern double physmem_total (void);
@ -394,6 +406,17 @@ extern void hex_init (void);
/* Save files used for communication between processes. */
#define PEX_SAVE_TEMPS 0x4
/* Max number of alloca bytes per call before we must switch to malloc.
?? Swiped from gnulib's regex_internal.h header. Is this actually
the case? This number seems arbitrary, though sane.
The OS usually guarantees only one guard page at the bottom of the stack,
and a page size can be as small as 4096 bytes. So we cannot safely
allocate anything larger than 4096 bytes. Also care for the possibility
of a few compiler-allocated temporary stack slots. */
#define MAX_ALLOCA_SIZE 4032
/* Prepare to execute one or more programs, with standard output of
each program fed to standard input of the next.
FLAGS As above.
@ -403,7 +426,7 @@ extern void hex_init (void);
Returns NULL on error. */
extern struct pex_obj *pex_init (int flags, const char *pname,
const char *tempbase);
const char *tempbase) ATTRIBUTE_RETURNS_NONNULL;
/* Flags for pex_run. These are bits to be or'ed together. */
@ -446,6 +469,11 @@ extern struct pex_obj *pex_init (int flags, const char *pname,
on Unix. */
#define PEX_BINARY_ERROR 0x80
/* Append stdout to existing file instead of truncating it. */
#define PEX_STDOUT_APPEND 0x100
/* Thes same as PEX_STDOUT_APPEND, but for STDERR. */
#define PEX_STDERR_APPEND 0x200
/* Execute one program. Returns NULL on success. On error returns an
error string (typically just the name of a system call); the error
@ -534,7 +562,7 @@ extern FILE *pex_input_file (struct pex_obj *obj, int flags,
extern FILE *pex_input_pipe (struct pex_obj *obj, int binary);
/* Read the standard output of the last program to be executed.
pex_run can not be called after this. BINARY should be non-zero if
pex_run cannot be called after this. BINARY should be non-zero if
the file should be opened in binary mode; this is ignored on Unix.
Returns NULL on error. Don't call fclose on the returned FILE; it
will be closed by pex_free. */
@ -542,7 +570,7 @@ extern FILE *pex_input_pipe (struct pex_obj *obj, int binary);
extern FILE *pex_read_output (struct pex_obj *, int binary);
/* Read the standard error of the last program to be executed.
pex_run can not be called after this. BINARY should be non-zero if
pex_run cannot be called after this. BINARY should be non-zero if
the file should be opened in binary mode; this is ignored on Unix.
Returns NULL on error. Don't call fclose on the returned FILE; it
will be closed by pex_free. */
@ -613,13 +641,18 @@ extern int pexecute (const char *, char * const *, const char *,
extern int pwait (int, int *, int);
#if !HAVE_DECL_ASPRINTF
#if defined(HAVE_DECL_ASPRINTF) && !HAVE_DECL_ASPRINTF
/* Like sprintf but provides a pointer to malloc'd storage, which must
be freed by the caller. */
extern int asprintf (char **, const char *, ...) ATTRIBUTE_PRINTF_2;
#endif
/* Like asprintf but allocates memory without fail. This works like
xmalloc. */
extern char *xasprintf (const char *, ...) ATTRIBUTE_MALLOC ATTRIBUTE_PRINTF_1;
#if !HAVE_DECL_VASPRINTF
/* Like vsprintf but provides a pointer to malloc'd storage, which
must be freed by the caller. */
@ -627,6 +660,11 @@ extern int asprintf (char **, const char *, ...) ATTRIBUTE_PRINTF_2;
extern int vasprintf (char **, const char *, va_list) ATTRIBUTE_PRINTF(2,0);
#endif
/* Like vasprintf but allocates memory without fail. This works like
xmalloc. */
extern char *xvasprintf (const char *, va_list) ATTRIBUTE_MALLOC ATTRIBUTE_PRINTF(1,0);
#if defined(HAVE_DECL_SNPRINTF) && !HAVE_DECL_SNPRINTF
/* Like sprintf but prints at most N characters. */
extern int snprintf (char *, size_t, const char *, ...) ATTRIBUTE_PRINTF_3;
@ -637,6 +675,37 @@ extern int snprintf (char *, size_t, const char *, ...) ATTRIBUTE_PRINTF_3;
extern int vsnprintf (char *, size_t, const char *, va_list) ATTRIBUTE_PRINTF(3,0);
#endif
#if defined (HAVE_DECL_STRNLEN) && !HAVE_DECL_STRNLEN
extern size_t strnlen (const char *, size_t);
#endif
#if defined(HAVE_DECL_STRVERSCMP) && !HAVE_DECL_STRVERSCMP
/* Compare version strings. */
extern int strverscmp (const char *, const char *);
#endif
#if defined(HAVE_DECL_STRTOL) && !HAVE_DECL_STRTOL
extern long int strtol (const char *nptr,
char **endptr, int base);
#endif
#if defined(HAVE_DECL_STRTOUL) && !HAVE_DECL_STRTOUL
extern unsigned long int strtoul (const char *nptr,
char **endptr, int base);
#endif
#if defined(HAVE_LONG_LONG) && defined(HAVE_DECL_STRTOLL) && !HAVE_DECL_STRTOLL
__extension__
extern long long int strtoll (const char *nptr,
char **endptr, int base);
#endif
#if defined(HAVE_LONG_LONG) && defined(HAVE_DECL_STRTOULL) && !HAVE_DECL_STRTOULL
__extension__
extern unsigned long long int strtoull (const char *nptr,
char **endptr, int base);
#endif
#if defined(HAVE_DECL_STRVERSCMP) && !HAVE_DECL_STRVERSCMP
/* Compare version strings. */
extern int strverscmp (const char *, const char *);
@ -664,7 +733,7 @@ extern void *C_alloca (size_t) ATTRIBUTE_MALLOC;
# define ASTRDUP(X) \
(__extension__ ({ const char *const libiberty_optr = (X); \
const unsigned long libiberty_len = strlen (libiberty_optr) + 1; \
char *const libiberty_nptr = (char *const) alloca (libiberty_len); \
char *const libiberty_nptr = (char *) alloca (libiberty_len); \
(char *) memcpy (libiberty_nptr, libiberty_optr, libiberty_len); }))
#else
# define alloca(x) C_alloca(x)

View file

@ -0,0 +1,49 @@
/* ###
* IP: LGPL 2.1
* NOTE: See binutils/libiberty/COPYING.LIB
*/
/* Internal demangler interface for the Rust programming language.
Copyright (C) 2016-2019 Free Software Foundation, Inc.
Written by David Tolnay (dtolnay@gmail.com).
This file is part of the libiberty library.
Libiberty is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
In addition to the permissions in the GNU Library General Public
License, the Free Software Foundation gives you unlimited permission
to link the compiled version of this file into combinations with other
programs, and to distribute those combinations without any restriction
coming from the use of this file. (The Library Public License
restrictions do apply in other respects; for example, they cover
modification of the file, and distribution when not linked into a
combined executable.)
Libiberty 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
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with libiberty; see the file COPYING.LIB.
If not, see <http://www.gnu.org/licenses/>. */
/* This file provides some definitions shared by cplus-dem.c and
rust-demangle.c. It should not be included by any other files. */
/* Returns non-zero iff MANGLED is a rust mangled symbol. MANGLED must
already have been demangled through cplus_demangle_v3. If this function
returns non-zero then MANGLED can be demangled (in-place) using
RUST_DEMANGLE_SYM. */
extern int
rust_is_mangled (const char *mangled);
/* Demangles SYM (in-place) if RUST_IS_MANGLED returned non-zero for SYM.
If RUST_IS_MANGLED returned zero for SYM then RUST_DEMANGLE_SYM might
replace characters that cannot be demangled with '?' and might truncate
SYM. After calling RUST_DEMANGLE_SYM SYM might be shorter, but never
larger. */
extern void
rust_demangle_sym (char *sym);

View file

@ -1,10 +1,10 @@
/* ###
* IP: LGPL 3.0
* REVIEWED: YES
* IP: LGPL 2.1
* NOTE: See binutils/include/COPYING
*/
/* <ctype.h> replacement macros.
Copyright (C) 2000, 2001 Free Software Foundation, Inc.
Copyright (C) 2000-2019 Free Software Foundation, Inc.
Contributed by Zack Weinberg <zackw@stanford.edu>.
This file is part of the libiberty library.

View file

@ -0,0 +1,94 @@
PURPOSE
This is a readme file to note the changes made to the binutils-2.24 source
code in order for Ghidra to build its GNU demangler.
COPIED SOURCE CODE / BUILDING RESTRICTIONS
Most of the files used to build the Ghidra GNU demangler are copied from binutils and have
not been changed. Further, the files in this directory are a small subset of the files used to
build the binutils suite. By copying specific files we are able to use Make and Visual Studio
to build a stand alone demangler without having to perform the more complicated build needed
to build binutils. Specifically, we do not have to run the configure utility that is
provided by binutils. This is critical, as we are using Visual Studio to build on Windows,
which does not have the configure utility support. If we ever wished to build the entire
binutils suite on Windows, then we would most likely need to use a GNU environment made for
Windows, such as MinGW.
CHANGES TO BINUTILS SOURCE
cplus-dem.c
To this file was added about 400 lines of source code. Previously, this file contained a
main method that we used to build our stand alone demangler. The current version of
binutils does not have this main method. Instead, binutils has only a main method in
cp-demangle.c for building the stand alone demangler. The c++filt utility is created using
a main method inside of cxxfilt.c. We could not build that utility without using the
more complicated build system mentioned above.
In order to gain full functionality contained in the c++filt utility, we copied the main
method from cxxfilt.c and placed it, along with supporting methods, into cplus-dem.c. This
allows us to perform a simple build of the stand alone demangler, with less source files
required.
cp-demangle.c *
This file contains a small, two-line change to send a newline character ('\n') along with
a flush to the output stream. Without this change, the program, when called repeatedly from
Ghidra would eventually hang. This is due to the nature of how Ghidra reads results in a
line-oriented fashion.
*This change is no longer used, as we do not use the main method inside of this file, but have
switched to the main method we made and placed into cplus-dem.c.
UPDATING
If we ever wish to update to a newer version of binutils, then we will need to re-copy the files
in this directory and then rebuild the main method we created inside of cplus-dem.c. That is,
unless at least one of the following changes happens:
1) the stand alone demangler in cp-demangle has full c++filt support, or
2) binutils has put the main method back inside cplus-dem.c, or
3) building a stand alone c++filt is simple enough that we can do it on each platform, or
4) we decide to build the entire binutils suite and use the full c++filt binary.
SOURCE FILES NEEDED BY OS
*nix / Mac
ansidecl.h
argv.c
cp-demangle.c
cp-demangle.h
cplus-dem.c
demangle.h
dyn-string.c
dyn-string.h
getopt.c
getopt.h
libiberty.h
safe-ctype.c
safe-ctype.h
xexit.c
xstrdup.c
WINDOWS
alloca.c
getopt1.c

View file

@ -0,0 +1,488 @@
/* ###
* IP: LGPL 2.1
* REVIEWED: YES
* NOTE: license is not in file, but in the directory from whence it came: binutils-2.24/libiberty/COPYING.LIB
*/
/* alloca.c -- allocate automatically reclaimed memory
(Mostly) portable public-domain implementation -- D A Gwyn
This implementation of the PWB library alloca function,
which is used to allocate space off the run-time stack so
that it is automatically reclaimed upon procedure exit,
was inspired by discussions with J. Q. Johnson of Cornell.
J.Otto Tennant <jot@cray.com> contributed the Cray support.
There are some preprocessor constants that can
be defined when compiling for your specific system, for
improved efficiency; however, the defaults should be okay.
The general concept of this implementation is to keep
track of all alloca-allocated blocks, and reclaim any
that are found to be deeper in the stack than the current
invocation. This heuristic does not reclaim storage as
soon as it becomes invalid, but it will do so eventually.
As a special case, alloca(0) reclaims storage without
allocating any. It is a good idea to use alloca(0) in
your main control loop, etc. to force garbage collection. */
/*
@deftypefn Replacement void* alloca (size_t @var{size})
This function allocates memory which will be automatically reclaimed
after the procedure exits. The @libib{} implementation does not free
the memory immediately but will do so eventually during subsequent
calls to this function. Memory is allocated using @code{xmalloc} under
normal circumstances.
The header file @file{alloca-conf.h} can be used in conjunction with the
GNU Autoconf test @code{AC_FUNC_ALLOCA} to test for and properly make
available this function. The @code{AC_FUNC_ALLOCA} test requires that
client code use a block of preprocessor code to be safe (see the Autoconf
manual for more); this header incorporates that logic and more, including
the possibility of a GCC built-in function.
@end deftypefn
*/
#ifdef HAVE_CONFIG_H
#include <config.h>
#endif
#include <libiberty.h>
#ifdef HAVE_STRING_H
#include <string.h>
#endif
#ifdef HAVE_STDLIB_H
#include <stdlib.h>
#endif
/* These variables are used by the ASTRDUP implementation that relies
on C_alloca. */
#ifdef __cplusplus
extern "C" {
#endif /* __cplusplus */
const char *libiberty_optr;
char *libiberty_nptr;
unsigned long libiberty_len;
#ifdef __cplusplus
}
#endif /* __cplusplus */
/* If your stack is a linked list of frames, you have to
provide an "address metric" ADDRESS_FUNCTION macro. */
#if defined (CRAY) && defined (CRAY_STACKSEG_END)
static long i00afunc ();
#define ADDRESS_FUNCTION(arg) (char *) i00afunc (&(arg))
#else
#define ADDRESS_FUNCTION(arg) &(arg)
#endif
#ifndef NULL
#define NULL 0
#endif
/* Define STACK_DIRECTION if you know the direction of stack
growth for your system; otherwise it will be automatically
deduced at run-time.
STACK_DIRECTION > 0 => grows toward higher addresses
STACK_DIRECTION < 0 => grows toward lower addresses
STACK_DIRECTION = 0 => direction of growth unknown */
#ifndef STACK_DIRECTION
#define STACK_DIRECTION 0 /* Direction unknown. */
#endif
#if STACK_DIRECTION != 0
#define STACK_DIR STACK_DIRECTION /* Known at compile-time. */
#else /* STACK_DIRECTION == 0; need run-time code. */
static int stack_dir; /* 1 or -1 once known. */
#define STACK_DIR stack_dir
static void
find_stack_direction (void)
{
static char *addr = NULL; /* Address of first `dummy', once known. */
auto char dummy; /* To get stack address. */
if (addr == NULL)
{ /* Initial entry. */
addr = ADDRESS_FUNCTION (dummy);
find_stack_direction (); /* Recurse once. */
}
else
{
/* Second entry. */
if (ADDRESS_FUNCTION (dummy) > addr)
stack_dir = 1; /* Stack grew upward. */
else
stack_dir = -1; /* Stack grew downward. */
}
}
#endif /* STACK_DIRECTION == 0 */
/* An "alloca header" is used to:
(a) chain together all alloca'ed blocks;
(b) keep track of stack depth.
It is very important that sizeof(header) agree with malloc
alignment chunk size. The following default should work okay. */
#ifndef ALIGN_SIZE
#define ALIGN_SIZE sizeof(double)
#endif
typedef union hdr
{
char align[ALIGN_SIZE]; /* To force sizeof(header). */
struct
{
union hdr *next; /* For chaining headers. */
char *deep; /* For stack depth measure. */
} h;
} header;
static header *last_alloca_header = NULL; /* -> last alloca header. */
/* Return a pointer to at least SIZE bytes of storage,
which will be automatically reclaimed upon exit from
the procedure that called alloca. Originally, this space
was supposed to be taken from the current stack frame of the
caller, but that method cannot be made to work for some
implementations of C, for example under Gould's UTX/32. */
/* @undocumented C_alloca */
PTR
C_alloca (size_t size)
{
auto char probe; /* Probes stack depth: */
register char *depth = ADDRESS_FUNCTION (probe);
#if STACK_DIRECTION == 0
if (STACK_DIR == 0) /* Unknown growth direction. */
find_stack_direction ();
#endif
/* Reclaim garbage, defined as all alloca'd storage that
was allocated from deeper in the stack than currently. */
{
register header *hp; /* Traverses linked list. */
for (hp = last_alloca_header; hp != NULL;)
if ((STACK_DIR > 0 && hp->h.deep > depth)
|| (STACK_DIR < 0 && hp->h.deep < depth))
{
register header *np = hp->h.next;
free ((PTR) hp); /* Collect garbage. */
hp = np; /* -> next header. */
}
else
break; /* Rest are not deeper. */
last_alloca_header = hp; /* -> last valid storage. */
}
if (size == 0)
return NULL; /* No allocation required. */
/* Allocate combined header + user data storage. */
{
register void *new_storage = XNEWVEC (char, sizeof (header) + size);
/* Address of header. */
if (new_storage == 0)
abort();
((header *) new_storage)->h.next = last_alloca_header;
((header *) new_storage)->h.deep = depth;
last_alloca_header = (header *) new_storage;
/* User storage begins just after header. */
return (PTR) ((char *) new_storage + sizeof (header));
}
}
#if defined (CRAY) && defined (CRAY_STACKSEG_END)
#ifdef DEBUG_I00AFUNC
#include <stdio.h>
#endif
#ifndef CRAY_STACK
#define CRAY_STACK
#ifndef CRAY2
/* Stack structures for CRAY-1, CRAY X-MP, and CRAY Y-MP */
struct stack_control_header
{
long shgrow:32; /* Number of times stack has grown. */
long shaseg:32; /* Size of increments to stack. */
long shhwm:32; /* High water mark of stack. */
long shsize:32; /* Current size of stack (all segments). */
};
/* The stack segment linkage control information occurs at
the high-address end of a stack segment. (The stack
grows from low addresses to high addresses.) The initial
part of the stack segment linkage control information is
0200 (octal) words. This provides for register storage
for the routine which overflows the stack. */
struct stack_segment_linkage
{
long ss[0200]; /* 0200 overflow words. */
long sssize:32; /* Number of words in this segment. */
long ssbase:32; /* Offset to stack base. */
long:32;
long sspseg:32; /* Offset to linkage control of previous
segment of stack. */
long:32;
long sstcpt:32; /* Pointer to task common address block. */
long sscsnm; /* Private control structure number for
microtasking. */
long ssusr1; /* Reserved for user. */
long ssusr2; /* Reserved for user. */
long sstpid; /* Process ID for pid based multi-tasking. */
long ssgvup; /* Pointer to multitasking thread giveup. */
long sscray[7]; /* Reserved for Cray Research. */
long ssa0;
long ssa1;
long ssa2;
long ssa3;
long ssa4;
long ssa5;
long ssa6;
long ssa7;
long sss0;
long sss1;
long sss2;
long sss3;
long sss4;
long sss5;
long sss6;
long sss7;
};
#else /* CRAY2 */
/* The following structure defines the vector of words
returned by the STKSTAT library routine. */
struct stk_stat
{
long now; /* Current total stack size. */
long maxc; /* Amount of contiguous space which would
be required to satisfy the maximum
stack demand to date. */
long high_water; /* Stack high-water mark. */
long overflows; /* Number of stack overflow ($STKOFEN) calls. */
long hits; /* Number of internal buffer hits. */
long extends; /* Number of block extensions. */
long stko_mallocs; /* Block allocations by $STKOFEN. */
long underflows; /* Number of stack underflow calls ($STKRETN). */
long stko_free; /* Number of deallocations by $STKRETN. */
long stkm_free; /* Number of deallocations by $STKMRET. */
long segments; /* Current number of stack segments. */
long maxs; /* Maximum number of stack segments so far. */
long pad_size; /* Stack pad size. */
long current_address; /* Current stack segment address. */
long current_size; /* Current stack segment size. This
number is actually corrupted by STKSTAT to
include the fifteen word trailer area. */
long initial_address; /* Address of initial segment. */
long initial_size; /* Size of initial segment. */
};
/* The following structure describes the data structure which trails
any stack segment. I think that the description in 'asdef' is
out of date. I only describe the parts that I am sure about. */
struct stk_trailer
{
long this_address; /* Address of this block. */
long this_size; /* Size of this block (does not include
this trailer). */
long unknown2;
long unknown3;
long link; /* Address of trailer block of previous
segment. */
long unknown5;
long unknown6;
long unknown7;
long unknown8;
long unknown9;
long unknown10;
long unknown11;
long unknown12;
long unknown13;
long unknown14;
};
#endif /* CRAY2 */
#endif /* not CRAY_STACK */
#ifdef CRAY2
/* Determine a "stack measure" for an arbitrary ADDRESS.
I doubt that "lint" will like this much. */
static long
i00afunc (long *address)
{
struct stk_stat status;
struct stk_trailer *trailer;
long *block, size;
long result = 0;
/* We want to iterate through all of the segments. The first
step is to get the stack status structure. We could do this
more quickly and more directly, perhaps, by referencing the
$LM00 common block, but I know that this works. */
STKSTAT (&status);
/* Set up the iteration. */
trailer = (struct stk_trailer *) (status.current_address
+ status.current_size
- 15);
/* There must be at least one stack segment. Therefore it is
a fatal error if "trailer" is null. */
if (trailer == 0)
abort ();
/* Discard segments that do not contain our argument address. */
while (trailer != 0)
{
block = (long *) trailer->this_address;
size = trailer->this_size;
if (block == 0 || size == 0)
abort ();
trailer = (struct stk_trailer *) trailer->link;
if ((block <= address) && (address < (block + size)))
break;
}
/* Set the result to the offset in this segment and add the sizes
of all predecessor segments. */
result = address - block;
if (trailer == 0)
{
return result;
}
do
{
if (trailer->this_size <= 0)
abort ();
result += trailer->this_size;
trailer = (struct stk_trailer *) trailer->link;
}
while (trailer != 0);
/* We are done. Note that if you present a bogus address (one
not in any segment), you will get a different number back, formed
from subtracting the address of the first block. This is probably
not what you want. */
return (result);
}
#else /* not CRAY2 */
/* Stack address function for a CRAY-1, CRAY X-MP, or CRAY Y-MP.
Determine the number of the cell within the stack,
given the address of the cell. The purpose of this
routine is to linearize, in some sense, stack addresses
for alloca. */
static long
i00afunc (long address)
{
long stkl = 0;
long size, pseg, this_segment, stack;
long result = 0;
struct stack_segment_linkage *ssptr;
/* Register B67 contains the address of the end of the
current stack segment. If you (as a subprogram) store
your registers on the stack and find that you are past
the contents of B67, you have overflowed the segment.
B67 also points to the stack segment linkage control
area, which is what we are really interested in. */
stkl = CRAY_STACKSEG_END ();
ssptr = (struct stack_segment_linkage *) stkl;
/* If one subtracts 'size' from the end of the segment,
one has the address of the first word of the segment.
If this is not the first segment, 'pseg' will be
nonzero. */
pseg = ssptr->sspseg;
size = ssptr->sssize;
this_segment = stkl - size;
/* It is possible that calling this routine itself caused
a stack overflow. Discard stack segments which do not
contain the target address. */
while (!(this_segment <= address && address <= stkl))
{
#ifdef DEBUG_I00AFUNC
fprintf (stderr, "%011o %011o %011o\n", this_segment, address, stkl);
#endif
if (pseg == 0)
break;
stkl = stkl - pseg;
ssptr = (struct stack_segment_linkage *) stkl;
size = ssptr->sssize;
pseg = ssptr->sspseg;
this_segment = stkl - size;
}
result = address - this_segment;
/* If you subtract pseg from the current end of the stack,
you get the address of the previous stack segment's end.
This seems a little convoluted to me, but I'll bet you save
a cycle somewhere. */
while (pseg != 0)
{
#ifdef DEBUG_I00AFUNC
fprintf (stderr, "%011o %011o\n", pseg, size);
#endif
stkl = stkl - pseg;
ssptr = (struct stack_segment_linkage *) stkl;
size = ssptr->sssize;
pseg = ssptr->sspseg;
result += size;
}
return (result);
}
#endif /* not CRAY2 */
#endif /* CRAY */

View file

@ -0,0 +1,545 @@
/* ###
* IP: LGPL 2.1
* REVIEWED: YES
* NOTE: from binutils 2.24
*/
/* Create and destroy argument vectors (argv's)
Copyright (C) 1992, 2001, 2010, 2012 Free Software Foundation, Inc.
Written by Fred Fish @ Cygnus Support
This file is part of the libiberty library.
Libiberty is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
Libiberty 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
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with libiberty; see the file COPYING.LIB. If
not, write to the Free Software Foundation, Inc., 51 Franklin Street - Fifth Floor,
Boston, MA 02110-1301, USA. */
/* Create and destroy argument vectors. An argument vector is simply an
array of string pointers, terminated by a NULL pointer. */
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
#include "ansidecl.h"
#include "libiberty.h"
#include "safe-ctype.h"
/* Routines imported from standard C runtime libraries. */
#include <stddef.h>
#include <string.h>
#include <stdlib.h>
#include <stdio.h>
#ifndef NULL
#define NULL 0
#endif
#ifndef EOS
#define EOS '\0'
#endif
#define INITIAL_MAXARGC 8 /* Number of args + NULL in initial argv */
/*
@deftypefn Extension char** dupargv (char **@var{vector})
Duplicate an argument vector. Simply scans through @var{vector},
duplicating each argument until the terminating @code{NULL} is found.
Returns a pointer to the argument vector if successful. Returns
@code{NULL} if there is insufficient memory to complete building the
argument vector.
@end deftypefn
*/
char **
dupargv (char **argv)
{
int argc;
char **copy;
if (argv == NULL)
return NULL;
/* the vector */
for (argc = 0; argv[argc] != NULL; argc++);
copy = (char **) xmalloc ((argc + 1) * sizeof (char *));
/* the strings */
for (argc = 0; argv[argc] != NULL; argc++)
{
int len = strlen (argv[argc]);
copy[argc] = (char *) xmalloc (len + 1);
strcpy (copy[argc], argv[argc]);
}
copy[argc] = NULL;
return copy;
}
/*
@deftypefn Extension void freeargv (char **@var{vector})
Free an argument vector that was built using @code{buildargv}. Simply
scans through @var{vector}, freeing the memory for each argument until
the terminating @code{NULL} is found, and then frees @var{vector}
itself.
@end deftypefn
*/
void freeargv (char **vector)
{
register char **scan;
if (vector != NULL)
{
for (scan = vector; *scan != NULL; scan++)
{
free (*scan);
}
free (vector);
}
}
static void
consume_whitespace (const char **input)
{
while (ISSPACE (**input))
{
(*input)++;
}
}
static int
only_whitespace (const char* input)
{
while (*input != EOS && ISSPACE (*input))
input++;
return (*input == EOS);
}
/*
@deftypefn Extension char** buildargv (char *@var{sp})
Given a pointer to a string, parse the string extracting fields
separated by whitespace and optionally enclosed within either single
or double quotes (which are stripped off), and build a vector of
pointers to copies of the string for each field. The input string
remains unchanged. The last element of the vector is followed by a
@code{NULL} element.
All of the memory for the pointer array and copies of the string
is obtained from @code{xmalloc}. All of the memory can be returned to the
system with the single function call @code{freeargv}, which takes the
returned result of @code{buildargv}, as it's argument.
Returns a pointer to the argument vector if successful. Returns
@code{NULL} if @var{sp} is @code{NULL} or if there is insufficient
memory to complete building the argument vector.
If the input is a null string (as opposed to a @code{NULL} pointer),
then buildarg returns an argument vector that has one arg, a null
string.
@end deftypefn
The memory for the argv array is dynamically expanded as necessary.
In order to provide a working buffer for extracting arguments into,
with appropriate stripping of quotes and translation of backslash
sequences, we allocate a working buffer at least as long as the input
string. This ensures that we always have enough space in which to
work, since the extracted arg is never larger than the input string.
The argument vector is always kept terminated with a @code{NULL} arg
pointer, so it can be passed to @code{freeargv} at any time, or
returned, as appropriate.
*/
char **buildargv (const char *input)
{
char *arg;
char *copybuf;
int squote = 0;
int dquote = 0;
int bsquote = 0;
int argc = 0;
int maxargc = 0;
char **argv = NULL;
char **nargv;
if (input != NULL)
{
copybuf = (char *) xmalloc (strlen (input) + 1);
/* Is a do{}while to always execute the loop once. Always return an
argv, even for null strings. See NOTES above, test case below. */
do
{
/* Pick off argv[argc] */
consume_whitespace (&input);
if ((maxargc == 0) || (argc >= (maxargc - 1)))
{
/* argv needs initialization, or expansion */
if (argv == NULL)
{
maxargc = INITIAL_MAXARGC;
nargv = (char **) xmalloc (maxargc * sizeof (char *));
}
else
{
maxargc *= 2;
nargv = (char **) xrealloc (argv, maxargc * sizeof (char *));
}
argv = nargv;
argv[argc] = NULL;
}
/* Begin scanning arg */
arg = copybuf;
while (*input != EOS)
{
if (ISSPACE (*input) && !squote && !dquote && !bsquote)
{
break;
}
else
{
if (bsquote)
{
bsquote = 0;
*arg++ = *input;
}
else if (*input == '\\')
{
bsquote = 1;
}
else if (squote)
{
if (*input == '\'')
{
squote = 0;
}
else
{
*arg++ = *input;
}
}
else if (dquote)
{
if (*input == '"')
{
dquote = 0;
}
else
{
*arg++ = *input;
}
}
else
{
if (*input == '\'')
{
squote = 1;
}
else if (*input == '"')
{
dquote = 1;
}
else
{
*arg++ = *input;
}
}
input++;
}
}
*arg = EOS;
argv[argc] = xstrdup (copybuf);
argc++;
argv[argc] = NULL;
consume_whitespace (&input);
}
while (*input != EOS);
free (copybuf);
}
return (argv);
}
/*
@deftypefn Extension int writeargv (const char **@var{argv}, FILE *@var{file})
Write each member of ARGV, handling all necessary quoting, to the file
named by FILE, separated by whitespace. Return 0 on success, non-zero
if an error occurred while writing to FILE.
@end deftypefn
*/
int
writeargv (char **argv, FILE *f)
{
int status = 0;
if (f == NULL)
return 1;
while (*argv != NULL)
{
const char *arg = *argv;
while (*arg != EOS)
{
char c = *arg;
if (ISSPACE(c) || c == '\\' || c == '\'' || c == '"')
if (EOF == fputc ('\\', f))
{
status = 1;
goto done;
}
if (EOF == fputc (c, f))
{
status = 1;
goto done;
}
arg++;
}
if (EOF == fputc ('\n', f))
{
status = 1;
goto done;
}
argv++;
}
done:
return status;
}
/*
@deftypefn Extension void expandargv (int *@var{argcp}, char ***@var{argvp})
The @var{argcp} and @code{argvp} arguments are pointers to the usual
@code{argc} and @code{argv} arguments to @code{main}. This function
looks for arguments that begin with the character @samp{@@}. Any such
arguments are interpreted as ``response files''. The contents of the
response file are interpreted as additional command line options. In
particular, the file is separated into whitespace-separated strings;
each such string is taken as a command-line option. The new options
are inserted in place of the option naming the response file, and
@code{*argcp} and @code{*argvp} will be updated. If the value of
@code{*argvp} is modified by this function, then the new value has
been dynamically allocated and can be deallocated by the caller with
@code{freeargv}. However, most callers will simply call
@code{expandargv} near the beginning of @code{main} and allow the
operating system to free the memory when the program exits.
@end deftypefn
*/
void
expandargv (int *argcp, char ***argvp)
{
/* The argument we are currently processing. */
int i = 0;
/* Non-zero if ***argvp has been dynamically allocated. */
int argv_dynamic = 0;
/* Limit the number of response files that we parse in order
to prevent infinite recursion. */
unsigned int iteration_limit = 2000;
/* Loop over the arguments, handling response files. We always skip
ARGVP[0], as that is the name of the program being run. */
while (++i < *argcp)
{
/* The name of the response file. */
const char *filename;
/* The response file. */
FILE *f;
/* An upper bound on the number of characters in the response
file. */
long pos;
/* The number of characters in the response file, when actually
read. */
size_t len;
/* A dynamically allocated buffer used to hold options read from a
response file. */
char *buffer;
/* Dynamically allocated storage for the options read from the
response file. */
char **file_argv;
/* The number of options read from the response file, if any. */
size_t file_argc;
/* We are only interested in options of the form "@file". */
filename = (*argvp)[i];
if (filename[0] != '@')
continue;
/* If we have iterated too many times then stop. */
if (-- iteration_limit == 0)
{
fprintf (stderr, "%s: error: too many @-files encountered\n", (*argvp)[0]);
xexit (1);
}
/* Read the contents of the file. */
f = fopen (++filename, "r");
if (!f)
continue;
if (fseek (f, 0L, SEEK_END) == -1)
goto error;
pos = ftell (f);
if (pos == -1)
goto error;
if (fseek (f, 0L, SEEK_SET) == -1)
goto error;
buffer = (char *) xmalloc (pos * sizeof (char) + 1);
len = fread (buffer, sizeof (char), pos, f);
if (len != (size_t) pos
/* On Windows, fread may return a value smaller than POS,
due to CR/LF->CR translation when reading text files.
That does not in-and-of itself indicate failure. */
&& ferror (f))
goto error;
/* Add a NUL terminator. */
buffer[len] = '\0';
/* If the file is empty or contains only whitespace, buildargv would
return a single empty argument. In this context we want no arguments,
instead. */
if (only_whitespace (buffer))
{
file_argv = (char **) xmalloc (sizeof (char *));
file_argv[0] = NULL;
}
else
/* Parse the string. */
file_argv = buildargv (buffer);
/* If *ARGVP is not already dynamically allocated, copy it. */
if (!argv_dynamic)
*argvp = dupargv (*argvp);
/* Count the number of arguments. */
file_argc = 0;
while (file_argv[file_argc])
++file_argc;
/* Now, insert FILE_ARGV into ARGV. The "+1" below handles the
NULL terminator at the end of ARGV. */
*argvp = ((char **)
xrealloc (*argvp,
(*argcp + file_argc + 1) * sizeof (char *)));
memmove (*argvp + i + file_argc, *argvp + i + 1,
(*argcp - i) * sizeof (char *));
memcpy (*argvp + i, file_argv, file_argc * sizeof (char *));
/* The original option has been replaced by all the new
options. */
*argcp += file_argc - 1;
/* Free up memory allocated to process the response file. We do
not use freeargv because the individual options in FILE_ARGV
are now in the main ARGV. */
free (file_argv);
free (buffer);
/* Rescan all of the arguments just read to support response
files that include other response files. */
--i;
error:
/* We're all done with the file now. */
fclose (f);
}
}
/*
@deftypefn Extension int countargv (char **@var{argv})
Return the number of elements in @var{argv}.
Returns zero if @var{argv} is NULL.
@end deftypefn
*/
int
countargv (char **argv)
{
int argc;
if (argv == NULL)
return 0;
for (argc = 0; argv[argc] != NULL; argc++)
continue;
return argc;
}
#ifdef MAIN
/* Simple little test driver. */
static const char *const tests[] =
{
"a simple command line",
"arg 'foo' is single quoted",
"arg \"bar\" is double quoted",
"arg \"foo bar\" has embedded whitespace",
"arg 'Jack said \\'hi\\'' has single quotes",
"arg 'Jack said \\\"hi\\\"' has double quotes",
"a b c d e f g h i j k l m n o p q r s t u v w x y z 1 2 3 4 5 6 7 8 9",
/* This should be expanded into only one argument. */
"trailing-whitespace ",
"",
NULL
};
int
main (void)
{
char **argv;
const char *const *test;
char **targs;
for (test = tests; *test != NULL; test++)
{
printf ("buildargv(\"%s\")\n", *test);
if ((argv = buildargv (*test)) == NULL)
{
printf ("failed!\n\n");
}
else
{
for (targs = argv; *targs != NULL; targs++)
{
printf ("\t\"%s\"\n", *targs);
}
printf ("\n");
}
freeargv (argv);
}
return 0;
}
#endif /* MAIN */

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,401 @@
/* ###
* IP: GPL 3 Linking Permitted
* REVIEWED: YES
*/
/* An abstract string datatype.
Copyright (C) 1998, 1999, 2000, 2002, 2004 Free Software Foundation, Inc.
Contributed by Mark Mitchell (mark@markmitchell.com).
This file is part of GNU CC.
GNU CC 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.
In addition to the permissions in the GNU General Public License, the
Free Software Foundation gives you unlimited permission to link the
compiled version of this file into combinations with other programs,
and to distribute those combinations without any restriction coming
from the use of this file. (The General Public License restrictions
do apply in other respects; for example, they cover modification of
the file, and distribution when not linked into a combined
executable.)
GNU CC 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 GNU CC; see the file COPYING. If not, write to
the Free Software Foundation, 51 Franklin Street - Fifth Floor,
Boston, MA 02110-1301, USA. */
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
#include <stdio.h>
#ifdef HAVE_STRING_H
#include <string.h>
#endif
#ifdef HAVE_STDLIB_H
#include <stdlib.h>
#endif
#include "libiberty.h"
#include "dyn-string.h"
/* Performs in-place initialization of a dyn_string struct. This
function can be used with a dyn_string struct on the stack or
embedded in another object. The contents of of the string itself
are still dynamically allocated. The string initially is capable
of holding at least SPACE characeters, including the terminating
NUL. If SPACE is 0, it will silently be increated to 1.
If RETURN_ON_ALLOCATION_FAILURE is defined and memory allocation
fails, returns 0. Otherwise returns 1. */
int
dyn_string_init (struct dyn_string *ds_struct_ptr, int space)
{
/* We need at least one byte in which to store the terminating NUL. */
if (space == 0)
space = 1;
#ifdef RETURN_ON_ALLOCATION_FAILURE
ds_struct_ptr->s = (char *) malloc (space);
if (ds_struct_ptr->s == NULL)
return 0;
#else
ds_struct_ptr->s = XNEWVEC (char, space);
#endif
ds_struct_ptr->allocated = space;
ds_struct_ptr->length = 0;
ds_struct_ptr->s[0] = '\0';
return 1;
}
/* Create a new dynamic string capable of holding at least SPACE
characters, including the terminating NUL. If SPACE is 0, it will
be silently increased to 1. If RETURN_ON_ALLOCATION_FAILURE is
defined and memory allocation fails, returns NULL. Otherwise
returns the newly allocated string. */
dyn_string_t
dyn_string_new (int space)
{
dyn_string_t result;
#ifdef RETURN_ON_ALLOCATION_FAILURE
result = (dyn_string_t) malloc (sizeof (struct dyn_string));
if (result == NULL)
return NULL;
if (!dyn_string_init (result, space))
{
free (result);
return NULL;
}
#else
result = XNEW (struct dyn_string);
dyn_string_init (result, space);
#endif
return result;
}
/* Free the memory used by DS. */
void
dyn_string_delete (dyn_string_t ds)
{
free (ds->s);
free (ds);
}
/* Returns the contents of DS in a buffer allocated with malloc. It
is the caller's responsibility to deallocate the buffer using free.
DS is then set to the empty string. Deletes DS itself. */
char*
dyn_string_release (dyn_string_t ds)
{
/* Store the old buffer. */
char* result = ds->s;
/* The buffer is no longer owned by DS. */
ds->s = NULL;
/* Delete DS. */
free (ds);
/* Return the old buffer. */
return result;
}
/* Increase the capacity of DS so it can hold at least SPACE
characters, plus the terminating NUL. This function will not (at
present) reduce the capacity of DS. Returns DS on success.
If RETURN_ON_ALLOCATION_FAILURE is defined and a memory allocation
operation fails, deletes DS and returns NULL. */
dyn_string_t
dyn_string_resize (dyn_string_t ds, int space)
{
int new_allocated = ds->allocated;
/* Increase SPACE to hold the NUL termination. */
++space;
/* Increase allocation by factors of two. */
while (space > new_allocated)
new_allocated *= 2;
if (new_allocated != ds->allocated)
{
ds->allocated = new_allocated;
/* We actually need more space. */
#ifdef RETURN_ON_ALLOCATION_FAILURE
ds->s = (char *) realloc (ds->s, ds->allocated);
if (ds->s == NULL)
{
free (ds);
return NULL;
}
#else
ds->s = XRESIZEVEC (char, ds->s, ds->allocated);
#endif
}
return ds;
}
/* Sets the contents of DS to the empty string. */
void
dyn_string_clear (dyn_string_t ds)
{
/* A dyn_string always has room for at least the NUL terminator. */
ds->s[0] = '\0';
ds->length = 0;
}
/* Makes the contents of DEST the same as the contents of SRC. DEST
and SRC must be distinct. Returns 1 on success. On failure, if
RETURN_ON_ALLOCATION_FAILURE, deletes DEST and returns 0. */
int
dyn_string_copy (dyn_string_t dest, dyn_string_t src)
{
if (dest == src)
abort ();
/* Make room in DEST. */
if (dyn_string_resize (dest, src->length) == NULL)
return 0;
/* Copy DEST into SRC. */
strcpy (dest->s, src->s);
/* Update the size of DEST. */
dest->length = src->length;
return 1;
}
/* Copies SRC, a NUL-terminated string, into DEST. Returns 1 on
success. On failure, if RETURN_ON_ALLOCATION_FAILURE, deletes DEST
and returns 0. */
int
dyn_string_copy_cstr (dyn_string_t dest, const char *src)
{
int length = strlen (src);
/* Make room in DEST. */
if (dyn_string_resize (dest, length) == NULL)
return 0;
/* Copy DEST into SRC. */
strcpy (dest->s, src);
/* Update the size of DEST. */
dest->length = length;
return 1;
}
/* Inserts SRC at the beginning of DEST. DEST is expanded as
necessary. SRC and DEST must be distinct. Returns 1 on success.
On failure, if RETURN_ON_ALLOCATION_FAILURE, deletes DEST and
returns 0. */
int
dyn_string_prepend (dyn_string_t dest, dyn_string_t src)
{
return dyn_string_insert (dest, 0, src);
}
/* Inserts SRC, a NUL-terminated string, at the beginning of DEST.
DEST is expanded as necessary. Returns 1 on success. On failure,
if RETURN_ON_ALLOCATION_FAILURE, deletes DEST and returns 0. */
int
dyn_string_prepend_cstr (dyn_string_t dest, const char *src)
{
return dyn_string_insert_cstr (dest, 0, src);
}
/* Inserts SRC into DEST starting at position POS. DEST is expanded
as necessary. SRC and DEST must be distinct. Returns 1 on
success. On failure, if RETURN_ON_ALLOCATION_FAILURE, deletes DEST
and returns 0. */
int
dyn_string_insert (dyn_string_t dest, int pos, dyn_string_t src)
{
int i;
if (src == dest)
abort ();
if (dyn_string_resize (dest, dest->length + src->length) == NULL)
return 0;
/* Make room for the insertion. Be sure to copy the NUL. */
for (i = dest->length; i >= pos; --i)
dest->s[i + src->length] = dest->s[i];
/* Splice in the new stuff. */
strncpy (dest->s + pos, src->s, src->length);
/* Compute the new length. */
dest->length += src->length;
return 1;
}
/* Inserts SRC, a NUL-terminated string, into DEST starting at
position POS. DEST is expanded as necessary. Returns 1 on
success. On failure, RETURN_ON_ALLOCATION_FAILURE, deletes DEST
and returns 0. */
int
dyn_string_insert_cstr (dyn_string_t dest, int pos, const char *src)
{
int i;
int length = strlen (src);
if (dyn_string_resize (dest, dest->length + length) == NULL)
return 0;
/* Make room for the insertion. Be sure to copy the NUL. */
for (i = dest->length; i >= pos; --i)
dest->s[i + length] = dest->s[i];
/* Splice in the new stuff. */
strncpy (dest->s + pos, src, length);
/* Compute the new length. */
dest->length += length;
return 1;
}
/* Inserts character C into DEST starting at position POS. DEST is
expanded as necessary. Returns 1 on success. On failure,
RETURN_ON_ALLOCATION_FAILURE, deletes DEST and returns 0. */
int
dyn_string_insert_char (dyn_string_t dest, int pos, int c)
{
int i;
if (dyn_string_resize (dest, dest->length + 1) == NULL)
return 0;
/* Make room for the insertion. Be sure to copy the NUL. */
for (i = dest->length; i >= pos; --i)
dest->s[i + 1] = dest->s[i];
/* Add the new character. */
dest->s[pos] = c;
/* Compute the new length. */
++dest->length;
return 1;
}
/* Append S to DS, resizing DS if necessary. Returns 1 on success.
On failure, if RETURN_ON_ALLOCATION_FAILURE, deletes DEST and
returns 0. */
int
dyn_string_append (dyn_string_t dest, dyn_string_t s)
{
if (dyn_string_resize (dest, dest->length + s->length) == 0)
return 0;
strcpy (dest->s + dest->length, s->s);
dest->length += s->length;
return 1;
}
/* Append the NUL-terminated string S to DS, resizing DS if necessary.
Returns 1 on success. On failure, if RETURN_ON_ALLOCATION_FAILURE,
deletes DEST and returns 0. */
int
dyn_string_append_cstr (dyn_string_t dest, const char *s)
{
int len = strlen (s);
/* The new length is the old length plus the size of our string, plus
one for the null at the end. */
if (dyn_string_resize (dest, dest->length + len) == NULL)
return 0;
strcpy (dest->s + dest->length, s);
dest->length += len;
return 1;
}
/* Appends C to the end of DEST. Returns 1 on success. On failure,
if RETURN_ON_ALLOCATION_FAILURE, deletes DEST and returns 0. */
int
dyn_string_append_char (dyn_string_t dest, int c)
{
/* Make room for the extra character. */
if (dyn_string_resize (dest, dest->length + 1) == NULL)
return 0;
/* Append the character; it will overwrite the old NUL. */
dest->s[dest->length] = c;
/* Add a new NUL at the end. */
dest->s[dest->length + 1] = '\0';
/* Update the length. */
++(dest->length);
return 1;
}
/* Sets the contents of DEST to the substring of SRC starting at START
and ending before END. START must be less than or equal to END,
and both must be between zero and the length of SRC, inclusive.
Returns 1 on success. On failure, if RETURN_ON_ALLOCATION_FAILURE,
deletes DEST and returns 0. */
int
dyn_string_substring (dyn_string_t dest, dyn_string_t src,
int start, int end)
{
int i;
int length = end - start;
if (start > end || start > src->length || end > src->length)
abort ();
/* Make room for the substring. */
if (dyn_string_resize (dest, length) == NULL)
return 0;
/* Copy the characters in the substring, */
for (i = length; --i >= 0; )
dest->s[i] = src->s[start + i];
/* NUL-terimate the result. */
dest->s[length] = '\0';
/* Record the length of the substring. */
dest->length = length;
return 1;
}
/* Returns non-zero if DS1 and DS2 have the same contents. */
int
dyn_string_eq (dyn_string_t ds1, dyn_string_t ds2)
{
/* If DS1 and DS2 have different lengths, they must not be the same. */
if (ds1->length != ds2->length)
return 0;
else
return !strcmp (ds1->s, ds2->s);
}

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,184 @@
/* ###
* IP: GPL 3
* REVIEWED: YES
*/
/* getopt_long and getopt_long_only entry points for GNU getopt.
Copyright (C) 1987,88,89,90,91,92,93,94,96,97,98,2005
Free Software Foundation, Inc.
NOTE: This source is derived from an old version taken from the GNU C
Library (glibc).
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, write to the Free Software
Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301,
USA. */
#ifdef HAVE_CONFIG_H
#include <config.h>
#endif
#if !defined __STDC__ || !__STDC__
/* This is a separate conditional since some stdc systems
reject `defined (const)'. */
#ifndef const
#define const
#endif
#endif
#include <stdio.h>
#include "getopt.h"
/* Comment out all this code if we are using the GNU C Library, and are not
actually compiling the library itself. This code is part of the GNU C
Library, but also included in many other GNU distributions. Compiling
and linking in this code is a waste when using the GNU C library
(especially if it is a shared library). Rather than having every GNU
program understand `configure --with-gnu-libc' and omit the object files,
it is simpler to just do this in the source for each such file. */
#define GETOPT_INTERFACE_VERSION 2
#if !defined _LIBC && defined __GLIBC__ && __GLIBC__ >= 2
#include <gnu-versions.h>
#if _GNU_GETOPT_INTERFACE_VERSION == GETOPT_INTERFACE_VERSION
#define ELIDE_CODE
#endif
#endif
#ifndef ELIDE_CODE
/* This needs to come after some library #include
to get __GNU_LIBRARY__ defined. */
#ifdef __GNU_LIBRARY__
#include <stdlib.h>
#endif
#ifndef NULL
#define NULL 0
#endif
int
getopt_long (int argc, char *const *argv, const char *options,
const struct option *long_options, int *opt_index)
{
return _getopt_internal (argc, argv, options, long_options, opt_index, 0);
}
/* Like getopt_long, but '-' as well as '--' can indicate a long option.
If an option that starts with '-' (not '--') doesn't match a long option,
but does match a short option, it is parsed as a short option
instead. */
int
getopt_long_only (int argc, char *const *argv, const char *options,
const struct option *long_options, int *opt_index)
{
return _getopt_internal (argc, argv, options, long_options, opt_index, 1);
}
#endif /* Not ELIDE_CODE. */
#ifdef TEST
#include <stdio.h>
int
main (int argc, char **argv)
{
int c;
int digit_optind = 0;
while (1)
{
int this_option_optind = optind ? optind : 1;
int option_index = 0;
static struct option long_options[] =
{
{"add", 1, 0, 0},
{"append", 0, 0, 0},
{"delete", 1, 0, 0},
{"verbose", 0, 0, 0},
{"create", 0, 0, 0},
{"file", 1, 0, 0},
{0, 0, 0, 0}
};
c = getopt_long (argc, argv, "abc:d:0123456789",
long_options, &option_index);
if (c == -1)
break;
switch (c)
{
case 0:
printf ("option %s", long_options[option_index].name);
if (optarg)
printf (" with arg %s", optarg);
printf ("\n");
break;
case '0':
case '1':
case '2':
case '3':
case '4':
case '5':
case '6':
case '7':
case '8':
case '9':
if (digit_optind != 0 && digit_optind != this_option_optind)
printf ("digits occur in two different argv-elements.\n");
digit_optind = this_option_optind;
printf ("option %c\n", c);
break;
case 'a':
printf ("option a\n");
break;
case 'b':
printf ("option b\n");
break;
case 'c':
printf ("option c with value `%s'\n", optarg);
break;
case 'd':
printf ("option d with value `%s'\n", optarg);
break;
case '?':
break;
default:
printf ("?? getopt returned character code 0%o ??\n", c);
}
}
if (optind < argc)
{
printf ("non-option ARGV-elements: ");
while (optind < argc)
printf ("%s ", argv[optind++]);
printf ("\n");
}
exit (0);
}
#endif /* TEST */

View file

@ -0,0 +1,259 @@
/* ###
* IP: LGPL 2.1
* REVIEWED: YES
*/
/* <ctype.h> replacement macros.
Copyright (C) 2000, 2001, 2002, 2003, 2004,
2005 Free Software Foundation, Inc.
Contributed by Zack Weinberg <zackw@stanford.edu>.
This file is part of the libiberty library.
Libiberty is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
Libiberty 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
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with libiberty; see the file COPYING.LIB. If
not, write to the Free Software Foundation, Inc., 51 Franklin Street - Fifth Floor,
Boston, MA 02110-1301, USA. */
/*
@defvr Extension HOST_CHARSET
This macro indicates the basic character set and encoding used by the
host: more precisely, the encoding used for character constants in
preprocessor @samp{#if} statements (the C "execution character set").
It is defined by @file{safe-ctype.h}, and will be an integer constant
with one of the following values:
@ftable @code
@item HOST_CHARSET_UNKNOWN
The host character set is unknown - that is, not one of the next two
possibilities.
@item HOST_CHARSET_ASCII
The host character set is ASCII.
@item HOST_CHARSET_EBCDIC
The host character set is some variant of EBCDIC. (Only one of the
nineteen EBCDIC varying characters is tested; exercise caution.)
@end ftable
@end defvr
@deffn Extension ISALPHA (@var{c})
@deffnx Extension ISALNUM (@var{c})
@deffnx Extension ISBLANK (@var{c})
@deffnx Extension ISCNTRL (@var{c})
@deffnx Extension ISDIGIT (@var{c})
@deffnx Extension ISGRAPH (@var{c})
@deffnx Extension ISLOWER (@var{c})
@deffnx Extension ISPRINT (@var{c})
@deffnx Extension ISPUNCT (@var{c})
@deffnx Extension ISSPACE (@var{c})
@deffnx Extension ISUPPER (@var{c})
@deffnx Extension ISXDIGIT (@var{c})
These twelve macros are defined by @file{safe-ctype.h}. Each has the
same meaning as the corresponding macro (with name in lowercase)
defined by the standard header @file{ctype.h}. For example,
@code{ISALPHA} returns true for alphabetic characters and false for
others. However, there are two differences between these macros and
those provided by @file{ctype.h}:
@itemize @bullet
@item These macros are guaranteed to have well-defined behavior for all
values representable by @code{signed char} and @code{unsigned char}, and
for @code{EOF}.
@item These macros ignore the current locale; they are true for these
fixed sets of characters:
@multitable {@code{XDIGIT}} {yada yada yada yada yada yada yada yada}
@item @code{ALPHA} @tab @kbd{A-Za-z}
@item @code{ALNUM} @tab @kbd{A-Za-z0-9}
@item @code{BLANK} @tab @kbd{space tab}
@item @code{CNTRL} @tab @code{!PRINT}
@item @code{DIGIT} @tab @kbd{0-9}
@item @code{GRAPH} @tab @code{ALNUM || PUNCT}
@item @code{LOWER} @tab @kbd{a-z}
@item @code{PRINT} @tab @code{GRAPH ||} @kbd{space}
@item @code{PUNCT} @tab @kbd{`~!@@#$%^&*()_-=+[@{]@}\|;:'",<.>/?}
@item @code{SPACE} @tab @kbd{space tab \n \r \f \v}
@item @code{UPPER} @tab @kbd{A-Z}
@item @code{XDIGIT} @tab @kbd{0-9A-Fa-f}
@end multitable
Note that, if the host character set is ASCII or a superset thereof,
all these macros will return false for all values of @code{char} outside
the range of 7-bit ASCII. In particular, both ISPRINT and ISCNTRL return
false for characters with numeric values from 128 to 255.
@end itemize
@end deffn
@deffn Extension ISIDNUM (@var{c})
@deffnx Extension ISIDST (@var{c})
@deffnx Extension IS_VSPACE (@var{c})
@deffnx Extension IS_NVSPACE (@var{c})
@deffnx Extension IS_SPACE_OR_NUL (@var{c})
@deffnx Extension IS_ISOBASIC (@var{c})
These six macros are defined by @file{safe-ctype.h} and provide
additional character classes which are useful when doing lexical
analysis of C or similar languages. They are true for the following
sets of characters:
@multitable {@code{SPACE_OR_NUL}} {yada yada yada yada yada yada yada yada}
@item @code{IDNUM} @tab @kbd{A-Za-z0-9_}
@item @code{IDST} @tab @kbd{A-Za-z_}
@item @code{VSPACE} @tab @kbd{\r \n}
@item @code{NVSPACE} @tab @kbd{space tab \f \v \0}
@item @code{SPACE_OR_NUL} @tab @code{VSPACE || NVSPACE}
@item @code{ISOBASIC} @tab @code{VSPACE || NVSPACE || PRINT}
@end multitable
@end deffn
*/
#include "ansidecl.h"
#include <safe-ctype.h>
#include <stdio.h> /* for EOF */
#if EOF != -1
#error "<safe-ctype.h> requires EOF == -1"
#endif
/* Shorthand */
#define bl _sch_isblank
#define cn _sch_iscntrl
#define di _sch_isdigit
#define is _sch_isidst
#define lo _sch_islower
#define nv _sch_isnvsp
#define pn _sch_ispunct
#define pr _sch_isprint
#define sp _sch_isspace
#define up _sch_isupper
#define vs _sch_isvsp
#define xd _sch_isxdigit
/* Masks. */
#define L (const unsigned short) (lo|is |pr) /* lower case letter */
#define XL (const unsigned short) (lo|is|xd|pr) /* lowercase hex digit */
#define U (const unsigned short) (up|is |pr) /* upper case letter */
#define XU (const unsigned short) (up|is|xd|pr) /* uppercase hex digit */
#define D (const unsigned short) (di |xd|pr) /* decimal digit */
#define P (const unsigned short) (pn |pr) /* punctuation */
#define _ (const unsigned short) (pn|is |pr) /* underscore */
#define C (const unsigned short) ( cn) /* control character */
#define Z (const unsigned short) (nv |cn) /* NUL */
#define M (const unsigned short) (nv|sp |cn) /* cursor movement: \f \v */
#define V (const unsigned short) (vs|sp |cn) /* vertical space: \r \n */
#define T (const unsigned short) (nv|sp|bl|cn) /* tab */
#define S (const unsigned short) (nv|sp|bl|pr) /* space */
/* Are we ASCII? */
#if HOST_CHARSET == HOST_CHARSET_ASCII
const unsigned short _sch_istable[256] =
{
Z, C, C, C, C, C, C, C, /* NUL SOH STX ETX EOT ENQ ACK BEL */
C, T, V, M, M, V, C, C, /* BS HT LF VT FF CR SO SI */
C, C, C, C, C, C, C, C, /* DLE DC1 DC2 DC3 DC4 NAK SYN ETB */
C, C, C, C, C, C, C, C, /* CAN EM SUB ESC FS GS RS US */
S, P, P, P, P, P, P, P, /* SP ! " # $ % & ' */
P, P, P, P, P, P, P, P, /* ( ) * + , - . / */
D, D, D, D, D, D, D, D, /* 0 1 2 3 4 5 6 7 */
D, D, P, P, P, P, P, P, /* 8 9 : ; < = > ? */
P, XU, XU, XU, XU, XU, XU, U, /* @ A B C D E F G */
U, U, U, U, U, U, U, U, /* H I J K L M N O */
U, U, U, U, U, U, U, U, /* P Q R S T U V W */
U, U, U, P, P, P, P, _, /* X Y Z [ \ ] ^ _ */
P, XL, XL, XL, XL, XL, XL, L, /* ` a b c d e f g */
L, L, L, L, L, L, L, L, /* h i j k l m n o */
L, L, L, L, L, L, L, L, /* p q r s t u v w */
L, L, L, P, P, P, P, C, /* x y z { | } ~ DEL */
/* high half of unsigned char is locale-specific, so all tests are
false in "C" locale */
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
};
const unsigned char _sch_tolower[256] =
{
0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15,
16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31,
32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47,
48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63,
64,
'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm',
'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z',
91, 92, 93, 94, 95, 96,
'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm',
'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z',
123,124,125,126,127,
128,129,130,131, 132,133,134,135, 136,137,138,139, 140,141,142,143,
144,145,146,147, 148,149,150,151, 152,153,154,155, 156,157,158,159,
160,161,162,163, 164,165,166,167, 168,169,170,171, 172,173,174,175,
176,177,178,179, 180,181,182,183, 184,185,186,187, 188,189,190,191,
192,193,194,195, 196,197,198,199, 200,201,202,203, 204,205,206,207,
208,209,210,211, 212,213,214,215, 216,217,218,219, 220,221,222,223,
224,225,226,227, 228,229,230,231, 232,233,234,235, 236,237,238,239,
240,241,242,243, 244,245,246,247, 248,249,250,251, 252,253,254,255,
};
const unsigned char _sch_toupper[256] =
{
0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15,
16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31,
32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47,
48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63,
64,
'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M',
'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z',
91, 92, 93, 94, 95, 96,
'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M',
'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z',
123,124,125,126,127,
128,129,130,131, 132,133,134,135, 136,137,138,139, 140,141,142,143,
144,145,146,147, 148,149,150,151, 152,153,154,155, 156,157,158,159,
160,161,162,163, 164,165,166,167, 168,169,170,171, 172,173,174,175,
176,177,178,179, 180,181,182,183, 184,185,186,187, 188,189,190,191,
192,193,194,195, 196,197,198,199, 200,201,202,203, 204,205,206,207,
208,209,210,211, 212,213,214,215, 216,217,218,219, 220,221,222,223,
224,225,226,227, 228,229,230,231, 232,233,234,235, 236,237,238,239,
240,241,242,243, 244,245,246,247, 248,249,250,251, 252,253,254,255,
};
#else
# if HOST_CHARSET == HOST_CHARSET_EBCDIC
#error "FIXME: write tables for EBCDIC"
# else
#error "Unrecognized host character set"
# endif
#endif

View file

@ -0,0 +1,56 @@
/* ###
* IP: LGPL 2.1
* REVIEWED: YES
*/
/* xexit.c -- Run any exit handlers, then exit.
Copyright (C) 1994, 95, 1997 Free Software Foundation, Inc.
This file is part of the libiberty library.
Libiberty is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
Libiberty 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
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with libiberty; see the file COPYING.LIB. If not, write
to the Free Software Foundation, Inc., 51 Franklin Street - Fifth Floor,
Boston, MA 02110-1301, USA. */
/*
@deftypefn Replacement void xexit (int @var{code})
Terminates the program. If any functions have been registered with
the @code{xatexit} replacement function, they will be called first.
Termination is handled via the system's normal @code{exit} call.
@end deftypefn
*/
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
#include <stdio.h>
#ifdef HAVE_STDLIB_H
#include <stdlib.h>
#endif
#include "libiberty.h"
/* This variable is set by xatexit if it is called. This way, xmalloc
doesn't drag xatexit into the link. */
void (*_xexit_cleanup) (void);
void
xexit (int code)
{
if (_xexit_cleanup != NULL)
(*_xexit_cleanup) ();
exit (code);
}

View file

@ -0,0 +1,41 @@
/* ###
* IP: LGPL 2.1
* REVIEWED: YES
* NOTE: license is not in file, but in the directory from whence it came: binutils-2.24/libiberty/COPYING.LIB
*/
/* xstrdup.c -- Duplicate a string in memory, using xmalloc.
This trivial function is in the public domain.
Ian Lance Taylor, Cygnus Support, December 1995. */
/*
@deftypefn Replacement char* xstrdup (const char *@var{s})
Duplicates a character string without fail, using @code{xmalloc} to
obtain memory.
@end deftypefn
*/
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
#include <sys/types.h>
#ifdef HAVE_STRING_H
#include <string.h>
#else
# ifdef HAVE_STRINGS_H
# include <strings.h>
# endif
#endif
#include "ansidecl.h"
#include "libiberty.h"
char *
xstrdup (const char *s)
{
register size_t len = strlen (s) + 1;
register char *ret = XNEWVEC (char, len);
return (char *) memcpy (ret, s, len);
}

View file

@ -0,0 +1,445 @@
/* ###
* IP: GPL 3
* REVIEWED: YES
*/
/* ANSI and traditional C compatability macros
Copyright 1991, 1992, 1993, 1994, 1995, 1996, 1998, 1999, 2000, 2001,
2002, 2003, 2004, 2005, 2006, 2007, 2009, 2010
Free Software Foundation, Inc.
This file is part of the GNU C Library.
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 of the License, 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, write to the Free Software
Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA. */
/* ANSI and traditional C compatibility macros
ANSI C is assumed if __STDC__ is #defined.
Macro ANSI C definition Traditional C definition
----- ---- - ---------- ----------- - ----------
ANSI_PROTOTYPES 1 not defined
PTR `void *' `char *'
PTRCONST `void *const' `char *'
LONG_DOUBLE `long double' `double'
const not defined `'
volatile not defined `'
signed not defined `'
VA_START(ap, var) va_start(ap, var) va_start(ap)
Note that it is safe to write "void foo();" indicating a function
with no return value, in all K+R compilers we have been able to test.
For declaring functions with prototypes, we also provide these:
PARAMS ((prototype))
-- for functions which take a fixed number of arguments. Use this
when declaring the function. When defining the function, write a
K+R style argument list. For example:
char *strcpy PARAMS ((char *dest, char *source));
...
char *
strcpy (dest, source)
char *dest;
char *source;
{ ... }
VPARAMS ((prototype, ...))
-- for functions which take a variable number of arguments. Use
PARAMS to declare the function, VPARAMS to define it. For example:
int printf PARAMS ((const char *format, ...));
...
int
printf VPARAMS ((const char *format, ...))
{
...
}
For writing functions which take variable numbers of arguments, we
also provide the VA_OPEN, VA_CLOSE, and VA_FIXEDARG macros. These
hide the differences between K+R <varargs.h> and C89 <stdarg.h> more
thoroughly than the simple VA_START() macro mentioned above.
VA_OPEN and VA_CLOSE are used *instead of* va_start and va_end.
Immediately after VA_OPEN, put a sequence of VA_FIXEDARG calls
corresponding to the list of fixed arguments. Then use va_arg
normally to get the variable arguments, or pass your va_list object
around. You do not declare the va_list yourself; VA_OPEN does it
for you.
Here is a complete example:
int
printf VPARAMS ((const char *format, ...))
{
int result;
VA_OPEN (ap, format);
VA_FIXEDARG (ap, const char *, format);
result = vfprintf (stdout, format, ap);
VA_CLOSE (ap);
return result;
}
You can declare variables either before or after the VA_OPEN,
VA_FIXEDARG sequence. Also, VA_OPEN and VA_CLOSE are the beginning
and end of a block. They must appear at the same nesting level,
and any variables declared after VA_OPEN go out of scope at
VA_CLOSE. Unfortunately, with a K+R compiler, that includes the
argument list. You can have multiple instances of VA_OPEN/VA_CLOSE
pairs in a single function in case you need to traverse the
argument list more than once.
For ease of writing code which uses GCC extensions but needs to be
portable to other compilers, we provide the GCC_VERSION macro that
simplifies testing __GNUC__ and __GNUC_MINOR__ together, and various
wrappers around __attribute__. Also, __extension__ will be #defined
to nothing if it doesn't work. See below.
This header also defines a lot of obsolete macros:
CONST, VOLATILE, SIGNED, PROTO, EXFUN, DEFUN, DEFUN_VOID,
AND, DOTS, NOARGS. Don't use them. */
#ifndef _ANSIDECL_H
#define _ANSIDECL_H 1
#ifdef __cplusplus
extern "C" {
#endif
/* Every source file includes this file,
so they will all get the switch for lint. */
/* LINTLIBRARY */
/* Using MACRO(x,y) in cpp #if conditionals does not work with some
older preprocessors. Thus we can't define something like this:
#define HAVE_GCC_VERSION(MAJOR, MINOR) \
(__GNUC__ > (MAJOR) || (__GNUC__ == (MAJOR) && __GNUC_MINOR__ >= (MINOR)))
and then test "#if HAVE_GCC_VERSION(2,7)".
So instead we use the macro below and test it against specific values. */
/* This macro simplifies testing whether we are using gcc, and if it
is of a particular minimum version. (Both major & minor numbers are
significant.) This macro will evaluate to 0 if we are not using
gcc at all. */
#ifndef GCC_VERSION
#define GCC_VERSION (__GNUC__ * 1000 + __GNUC_MINOR__)
#endif /* GCC_VERSION */
#if defined (__STDC__) || defined(__cplusplus) || defined (_AIX) || (defined (__mips) && defined (_SYSTYPE_SVR4)) || defined(_WIN32)
/* All known AIX compilers implement these things (but don't always
define __STDC__). The RISC/OS MIPS compiler defines these things
in SVR4 mode, but does not define __STDC__. */
/* eraxxon@alumni.rice.edu: The Compaq C++ compiler, unlike many other
C++ compilers, does not define __STDC__, though it acts as if this
was so. (Verified versions: 5.7, 6.2, 6.3, 6.5) */
#define ANSI_PROTOTYPES 1
#define PTR void *
#define PTRCONST void *const
#define LONG_DOUBLE long double
/* PARAMS is often defined elsewhere (e.g. by libintl.h), so wrap it in
a #ifndef. */
#ifndef PARAMS
#define PARAMS(ARGS) ARGS
#endif
#define VPARAMS(ARGS) ARGS
#define VA_START(VA_LIST, VAR) va_start(VA_LIST, VAR)
/* variadic function helper macros */
/* "struct Qdmy" swallows the semicolon after VA_OPEN/VA_FIXEDARG's
use without inhibiting further decls and without declaring an
actual variable. */
#define VA_OPEN(AP, VAR) { va_list AP; va_start(AP, VAR); { struct Qdmy
#define VA_CLOSE(AP) } va_end(AP); }
#define VA_FIXEDARG(AP, T, N) struct Qdmy
#undef const
#undef volatile
#undef signed
/* inline requires special treatment; it's in C99, and GCC >=2.7 supports
it too, but it's not in C89. */
#undef inline
#if __STDC_VERSION__ >= 199901L || defined(__cplusplus) || (defined(__SUNPRO_C) && defined(__C99FEATURES__))
/* it's a keyword */
#else
# if GCC_VERSION >= 2007
# define inline __inline__ /* __inline__ prevents -pedantic warnings */
# else
# define inline /* nothing */
# endif
#endif
/* These are obsolete. Do not use. */
#ifndef IN_GCC
#define CONST const
#define VOLATILE volatile
#define SIGNED signed
#define PROTO(type, name, arglist) type name arglist
#define EXFUN(name, proto) name proto
#define DEFUN(name, arglist, args) name(args)
#define DEFUN_VOID(name) name(void)
#define AND ,
#define DOTS , ...
#define NOARGS void
#endif /* ! IN_GCC */
#else /* Not ANSI C. */
#undef ANSI_PROTOTYPES
#define PTR char *
#define PTRCONST PTR
#define LONG_DOUBLE double
#define PARAMS(args) ()
#define VPARAMS(args) (va_alist) va_dcl
#define VA_START(va_list, var) va_start(va_list)
#define VA_OPEN(AP, VAR) { va_list AP; va_start(AP); { struct Qdmy
#define VA_CLOSE(AP) } va_end(AP); }
#define VA_FIXEDARG(AP, TYPE, NAME) TYPE NAME = va_arg(AP, TYPE)
/* some systems define these in header files for non-ansi mode */
#undef const
#undef volatile
#undef signed
#undef inline
#define const
#define volatile
#define signed
#define inline
#ifndef IN_GCC
#define CONST
#define VOLATILE
#define SIGNED
#define PROTO(type, name, arglist) type name ()
#define EXFUN(name, proto) name()
#define DEFUN(name, arglist, args) name arglist args;
#define DEFUN_VOID(name) name()
#define AND ;
#define DOTS
#define NOARGS
#endif /* ! IN_GCC */
#endif /* ANSI C. */
/* Define macros for some gcc attributes. This permits us to use the
macros freely, and know that they will come into play for the
version of gcc in which they are supported. */
#if (GCC_VERSION < 2007)
# define __attribute__(x)
#endif
/* Attribute __malloc__ on functions was valid as of gcc 2.96. */
#ifndef ATTRIBUTE_MALLOC
# if (GCC_VERSION >= 2096)
# define ATTRIBUTE_MALLOC __attribute__ ((__malloc__))
# else
# define ATTRIBUTE_MALLOC
# endif /* GNUC >= 2.96 */
#endif /* ATTRIBUTE_MALLOC */
/* Attributes on labels were valid as of gcc 2.93 and g++ 4.5. For
g++ an attribute on a label must be followed by a semicolon. */
#ifndef ATTRIBUTE_UNUSED_LABEL
# ifndef __cplusplus
# if GCC_VERSION >= 2093
# define ATTRIBUTE_UNUSED_LABEL ATTRIBUTE_UNUSED
# else
# define ATTRIBUTE_UNUSED_LABEL
# endif
# else
# if GCC_VERSION >= 4005
# define ATTRIBUTE_UNUSED_LABEL ATTRIBUTE_UNUSED ;
# else
# define ATTRIBUTE_UNUSED_LABEL
# endif
# endif
#endif
/* Similarly to ARG_UNUSED below. Prior to GCC 3.4, the C++ frontend
couldn't parse attributes placed after the identifier name, and now
the entire compiler is built with C++. */
#ifndef ATTRIBUTE_UNUSED
#if GCC_VERSION >= 3004
# define ATTRIBUTE_UNUSED __attribute__ ((__unused__))
#else
#define ATTRIBUTE_UNUSED
#endif
#endif /* ATTRIBUTE_UNUSED */
/* Before GCC 3.4, the C++ frontend couldn't parse attributes placed after the
identifier name. */
#if ! defined(__cplusplus) || (GCC_VERSION >= 3004)
# define ARG_UNUSED(NAME) NAME ATTRIBUTE_UNUSED
#else /* !__cplusplus || GNUC >= 3.4 */
# define ARG_UNUSED(NAME) NAME
#endif /* !__cplusplus || GNUC >= 3.4 */
#ifndef ATTRIBUTE_NORETURN
#define ATTRIBUTE_NORETURN __attribute__ ((__noreturn__))
#endif /* ATTRIBUTE_NORETURN */
/* Attribute `nonnull' was valid as of gcc 3.3. */
#ifndef ATTRIBUTE_NONNULL
# if (GCC_VERSION >= 3003)
# define ATTRIBUTE_NONNULL(m) __attribute__ ((__nonnull__ (m)))
# else
# define ATTRIBUTE_NONNULL(m)
# endif /* GNUC >= 3.3 */
#endif /* ATTRIBUTE_NONNULL */
/* Attribute `pure' was valid as of gcc 3.0. */
#ifndef ATTRIBUTE_PURE
# if (GCC_VERSION >= 3000)
# define ATTRIBUTE_PURE __attribute__ ((__pure__))
# else
# define ATTRIBUTE_PURE
# endif /* GNUC >= 3.0 */
#endif /* ATTRIBUTE_PURE */
/* Use ATTRIBUTE_PRINTF when the format specifier must not be NULL.
This was the case for the `printf' format attribute by itself
before GCC 3.3, but as of 3.3 we need to add the `nonnull'
attribute to retain this behavior. */
#ifndef ATTRIBUTE_PRINTF
#define ATTRIBUTE_PRINTF(m, n) __attribute__ ((__format__ (__printf__, m, n))) ATTRIBUTE_NONNULL(m)
#define ATTRIBUTE_PRINTF_1 ATTRIBUTE_PRINTF(1, 2)
#define ATTRIBUTE_PRINTF_2 ATTRIBUTE_PRINTF(2, 3)
#define ATTRIBUTE_PRINTF_3 ATTRIBUTE_PRINTF(3, 4)
#define ATTRIBUTE_PRINTF_4 ATTRIBUTE_PRINTF(4, 5)
#define ATTRIBUTE_PRINTF_5 ATTRIBUTE_PRINTF(5, 6)
#endif /* ATTRIBUTE_PRINTF */
/* Use ATTRIBUTE_FPTR_PRINTF when the format attribute is to be set on
a function pointer. Format attributes were allowed on function
pointers as of gcc 3.1. */
#ifndef ATTRIBUTE_FPTR_PRINTF
# if (GCC_VERSION >= 3001)
# define ATTRIBUTE_FPTR_PRINTF(m, n) ATTRIBUTE_PRINTF(m, n)
# else
# define ATTRIBUTE_FPTR_PRINTF(m, n)
# endif /* GNUC >= 3.1 */
# define ATTRIBUTE_FPTR_PRINTF_1 ATTRIBUTE_FPTR_PRINTF(1, 2)
# define ATTRIBUTE_FPTR_PRINTF_2 ATTRIBUTE_FPTR_PRINTF(2, 3)
# define ATTRIBUTE_FPTR_PRINTF_3 ATTRIBUTE_FPTR_PRINTF(3, 4)
# define ATTRIBUTE_FPTR_PRINTF_4 ATTRIBUTE_FPTR_PRINTF(4, 5)
# define ATTRIBUTE_FPTR_PRINTF_5 ATTRIBUTE_FPTR_PRINTF(5, 6)
#endif /* ATTRIBUTE_FPTR_PRINTF */
/* Use ATTRIBUTE_NULL_PRINTF when the format specifier may be NULL. A
NULL format specifier was allowed as of gcc 3.3. */
#ifndef ATTRIBUTE_NULL_PRINTF
# if (GCC_VERSION >= 3003)
# define ATTRIBUTE_NULL_PRINTF(m, n) __attribute__ ((__format__ (__printf__, m, n)))
# else
# define ATTRIBUTE_NULL_PRINTF(m, n)
# endif /* GNUC >= 3.3 */
# define ATTRIBUTE_NULL_PRINTF_1 ATTRIBUTE_NULL_PRINTF(1, 2)
# define ATTRIBUTE_NULL_PRINTF_2 ATTRIBUTE_NULL_PRINTF(2, 3)
# define ATTRIBUTE_NULL_PRINTF_3 ATTRIBUTE_NULL_PRINTF(3, 4)
# define ATTRIBUTE_NULL_PRINTF_4 ATTRIBUTE_NULL_PRINTF(4, 5)
# define ATTRIBUTE_NULL_PRINTF_5 ATTRIBUTE_NULL_PRINTF(5, 6)
#endif /* ATTRIBUTE_NULL_PRINTF */
/* Attribute `sentinel' was valid as of gcc 3.5. */
#ifndef ATTRIBUTE_SENTINEL
# if (GCC_VERSION >= 3005)
# define ATTRIBUTE_SENTINEL __attribute__ ((__sentinel__))
# else
# define ATTRIBUTE_SENTINEL
# endif /* GNUC >= 3.5 */
#endif /* ATTRIBUTE_SENTINEL */
#ifndef ATTRIBUTE_ALIGNED_ALIGNOF
# if (GCC_VERSION >= 3000)
# define ATTRIBUTE_ALIGNED_ALIGNOF(m) __attribute__ ((__aligned__ (__alignof__ (m))))
# else
# define ATTRIBUTE_ALIGNED_ALIGNOF(m)
# endif /* GNUC >= 3.0 */
#endif /* ATTRIBUTE_ALIGNED_ALIGNOF */
/* Useful for structures whose layout must much some binary specification
regardless of the alignment and padding qualities of the compiler. */
#ifndef ATTRIBUTE_PACKED
# define ATTRIBUTE_PACKED __attribute__ ((packed))
#endif
/* Attribute `hot' and `cold' was valid as of gcc 4.3. */
#ifndef ATTRIBUTE_COLD
# if (GCC_VERSION >= 4003)
# define ATTRIBUTE_COLD __attribute__ ((__cold__))
# else
# define ATTRIBUTE_COLD
# endif /* GNUC >= 4.3 */
#endif /* ATTRIBUTE_COLD */
#ifndef ATTRIBUTE_HOT
# if (GCC_VERSION >= 4003)
# define ATTRIBUTE_HOT __attribute__ ((__hot__))
# else
# define ATTRIBUTE_HOT
# endif /* GNUC >= 4.3 */
#endif /* ATTRIBUTE_HOT */
/* We use __extension__ in some places to suppress -pedantic warnings
about GCC extensions. This feature didn't work properly before
gcc 2.8. */
#if GCC_VERSION < 2008
#define __extension__
#endif
/* This is used to declare a const variable which should be visible
outside of the current compilation unit. Use it as
EXPORTED_CONST int i = 1;
This is because the semantics of const are different in C and C++.
"extern const" is permitted in C but it looks strange, and gcc
warns about it when -Wc++-compat is not used. */
#ifdef __cplusplus
#define EXPORTED_CONST extern const
#else
#define EXPORTED_CONST const
#endif
/* Be conservative and only use enum bitfields with C++ or GCC.
FIXME: provide a complete autoconf test for buggy enum bitfields. */
#ifdef __cplusplus
#define ENUM_BITFIELD(TYPE) enum TYPE
#elif (GCC_VERSION > 2000)
#define ENUM_BITFIELD(TYPE) __extension__ enum TYPE
#else
#define ENUM_BITFIELD(TYPE) unsigned int
#endif
#ifdef __cplusplus
}
#endif
#endif /* ansidecl.h */

View file

@ -0,0 +1,172 @@
/* ###
* IP: GPL 3 Linking Permitted
*/
/* Internal demangler interface for g++ V3 ABI.
Copyright (C) 2003, 2004, 2005, 2006, 2007, 2010
Free Software Foundation, Inc.
Written by Ian Lance Taylor <ian@wasabisystems.com>.
This file is part of the libiberty library, which is part of GCC.
This file 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 of the License, or
(at your option) any later version.
In addition to the permissions in the GNU General Public License, the
Free Software Foundation gives you unlimited permission to link the
compiled version of this file into combinations with other programs,
and to distribute those combinations without any restriction coming
from the use of this file. (The General Public License restrictions
do apply in other respects; for example, they cover modification of
the file, and distribution when not linked into a combined
executable.)
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, write to the Free Software
Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA.
*/
/* This file provides some definitions shared by cp-demangle.c and
cp-demint.c. It should not be included by any other files. */
/* Information we keep for operators. */
struct demangle_operator_info
{
/* Mangled name. */
const char *code;
/* Real name. */
const char *name;
/* Length of real name. */
int len;
/* Number of arguments. */
int args;
};
/* How to print the value of a builtin type. */
enum d_builtin_type_print
{
/* Print as (type)val. */
D_PRINT_DEFAULT,
/* Print as integer. */
D_PRINT_INT,
/* Print as unsigned integer, with trailing "u". */
D_PRINT_UNSIGNED,
/* Print as long, with trailing "l". */
D_PRINT_LONG,
/* Print as unsigned long, with trailing "ul". */
D_PRINT_UNSIGNED_LONG,
/* Print as long long, with trailing "ll". */
D_PRINT_LONG_LONG,
/* Print as unsigned long long, with trailing "ull". */
D_PRINT_UNSIGNED_LONG_LONG,
/* Print as bool. */
D_PRINT_BOOL,
/* Print as float--put value in square brackets. */
D_PRINT_FLOAT,
/* Print in usual way, but here to detect void. */
D_PRINT_VOID
};
/* Information we keep for a builtin type. */
struct demangle_builtin_type_info
{
/* Type name. */
const char *name;
/* Length of type name. */
int len;
/* Type name when using Java. */
const char *java_name;
/* Length of java name. */
int java_len;
/* How to print a value of this type. */
enum d_builtin_type_print print;
};
/* The information structure we pass around. */
struct d_info
{
/* The string we are demangling. */
const char *s;
/* The end of the string we are demangling. */
const char *send;
/* The options passed to the demangler. */
int options;
/* The next character in the string to consider. */
const char *n;
/* The array of components. */
struct demangle_component *comps;
/* The index of the next available component. */
int next_comp;
/* The number of available component structures. */
int num_comps;
/* The array of substitutions. */
struct demangle_component **subs;
/* The index of the next substitution. */
int next_sub;
/* The number of available entries in the subs array. */
int num_subs;
/* The number of substitutions which we actually made from the subs
array, plus the number of template parameter references we
saw. */
int did_subs;
/* The last name we saw, for constructors and destructors. */
struct demangle_component *last_name;
/* A running total of the length of large expansions from the
mangled name to the demangled name, such as standard
substitutions and builtin types. */
int expansion;
};
/* To avoid running past the ending '\0', don't:
- call d_peek_next_char if d_peek_char returned '\0'
- call d_advance with an 'i' that is too large
- call d_check_char(di, '\0')
Everything else is safe. */
#define d_peek_char(di) (*((di)->n))
#define d_peek_next_char(di) ((di)->n[1])
#define d_advance(di, i) ((di)->n += (i))
#define d_check_char(di, c) (d_peek_char(di) == c ? ((di)->n++, 1) : 0)
#define d_next_char(di) (d_peek_char(di) == '\0' ? '\0' : *((di)->n++))
#define d_str(di) ((di)->n)
/* Functions and arrays in cp-demangle.c which are referenced by
functions in cp-demint.c. */
#ifdef IN_GLIBCPP_V3
#define CP_STATIC_IF_GLIBCPP_V3 static
#else
#define CP_STATIC_IF_GLIBCPP_V3 extern
#endif
#ifndef IN_GLIBCPP_V3
extern const struct demangle_operator_info cplus_demangle_operators[];
#endif
#define D_BUILTIN_TYPE_COUNT (34)
CP_STATIC_IF_GLIBCPP_V3
const struct demangle_builtin_type_info
cplus_demangle_builtin_types[D_BUILTIN_TYPE_COUNT];
CP_STATIC_IF_GLIBCPP_V3
struct demangle_component *
cplus_demangle_mangled_name (struct d_info *, int);
CP_STATIC_IF_GLIBCPP_V3
struct demangle_component *
cplus_demangle_type (struct d_info *);
extern void
cplus_demangle_init_info (const char *, int, size_t, struct d_info *);
/* cp-demangle.c needs to define this a little differently */
#undef CP_STATIC_IF_GLIBCPP_V3

View file

@ -0,0 +1,675 @@
/* ###
* IP: LGPL 3.0
* REVIEWED: YES
*/
/* Defs for interface to demanglers.
Copyright 1992, 1993, 1994, 1995, 1996, 1997, 1998, 2000, 2001, 2002,
2003, 2004, 2005, 2007, 2008, 2009, 2010 Free Software Foundation, Inc.
This program is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public License
as published by the Free Software Foundation; either version 2, or
(at your option) any later version.
In addition to the permissions in the GNU Library General Public
License, the Free Software Foundation gives you unlimited
permission to link the compiled version of this file into
combinations with other programs, and to distribute those
combinations without any restriction coming from the use of this
file. (The Library Public License restrictions do apply in other
respects; for example, they cover modification of the file, and
distribution when not linked into a combined executable.)
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
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA
02110-1301, USA. */
#if !defined (DEMANGLE_H)
#define DEMANGLE_H
#include "libiberty.h"
#ifdef __cplusplus
extern "C" {
#endif /* __cplusplus */
/* Options passed to cplus_demangle (in 2nd parameter). */
#define DMGL_NO_OPTS 0 /* For readability... */
#define DMGL_PARAMS (1 << 0) /* Include function args */
#define DMGL_ANSI (1 << 1) /* Include const, volatile, etc */
#define DMGL_JAVA (1 << 2) /* Demangle as Java rather than C++. */
#define DMGL_VERBOSE (1 << 3) /* Include implementation details. */
#define DMGL_TYPES (1 << 4) /* Also try to demangle type encodings. */
#define DMGL_RET_POSTFIX (1 << 5) /* Print function return types (when
present) after function signature.
It applies only to the toplevel
function type. */
#define DMGL_RET_DROP (1 << 6) /* Suppress printing function return
types, even if present. It applies
only to the toplevel function type.
*/
#define DMGL_AUTO (1 << 8)
#define DMGL_GNU (1 << 9)
#define DMGL_LUCID (1 << 10)
#define DMGL_ARM (1 << 11)
#define DMGL_HP (1 << 12) /* For the HP aCC compiler;
same as ARM except for
template arguments, etc. */
#define DMGL_EDG (1 << 13)
#define DMGL_GNU_V3 (1 << 14)
#define DMGL_GNAT (1 << 15)
/* If none of these are set, use 'current_demangling_style' as the default. */
#define DMGL_STYLE_MASK (DMGL_AUTO|DMGL_GNU|DMGL_LUCID|DMGL_ARM|DMGL_HP|DMGL_EDG|DMGL_GNU_V3|DMGL_JAVA|DMGL_GNAT)
/* Enumeration of possible demangling styles.
Lucid and ARM styles are still kept logically distinct, even though
they now both behave identically. The resulting style is actual the
union of both. I.E. either style recognizes both "__pt__" and "__rf__"
for operator "->", even though the first is lucid style and the second
is ARM style. (FIXME?) */
extern enum demangling_styles
{
no_demangling = -1,
unknown_demangling = 0,
auto_demangling = DMGL_AUTO,
gnu_demangling = DMGL_GNU,
lucid_demangling = DMGL_LUCID,
arm_demangling = DMGL_ARM,
hp_demangling = DMGL_HP,
edg_demangling = DMGL_EDG,
gnu_v3_demangling = DMGL_GNU_V3,
java_demangling = DMGL_JAVA,
gnat_demangling = DMGL_GNAT
} current_demangling_style;
/* Define string names for the various demangling styles. */
#define NO_DEMANGLING_STYLE_STRING "none"
#define AUTO_DEMANGLING_STYLE_STRING "auto"
#define GNU_DEMANGLING_STYLE_STRING "gnu"
#define LUCID_DEMANGLING_STYLE_STRING "lucid"
#define ARM_DEMANGLING_STYLE_STRING "arm"
#define HP_DEMANGLING_STYLE_STRING "hp"
#define EDG_DEMANGLING_STYLE_STRING "edg"
#define GNU_V3_DEMANGLING_STYLE_STRING "gnu-v3"
#define JAVA_DEMANGLING_STYLE_STRING "java"
#define GNAT_DEMANGLING_STYLE_STRING "gnat"
/* Some macros to test what demangling style is active. */
#define CURRENT_DEMANGLING_STYLE current_demangling_style
#define AUTO_DEMANGLING (((int) CURRENT_DEMANGLING_STYLE) & DMGL_AUTO)
#define GNU_DEMANGLING (((int) CURRENT_DEMANGLING_STYLE) & DMGL_GNU)
#define LUCID_DEMANGLING (((int) CURRENT_DEMANGLING_STYLE) & DMGL_LUCID)
#define ARM_DEMANGLING (((int) CURRENT_DEMANGLING_STYLE) & DMGL_ARM)
#define HP_DEMANGLING (((int) CURRENT_DEMANGLING_STYLE) & DMGL_HP)
#define EDG_DEMANGLING (((int) CURRENT_DEMANGLING_STYLE) & DMGL_EDG)
#define GNU_V3_DEMANGLING (((int) CURRENT_DEMANGLING_STYLE) & DMGL_GNU_V3)
#define JAVA_DEMANGLING (((int) CURRENT_DEMANGLING_STYLE) & DMGL_JAVA)
#define GNAT_DEMANGLING (((int) CURRENT_DEMANGLING_STYLE) & DMGL_GNAT)
/* Provide information about the available demangle styles. This code is
pulled from gdb into libiberty because it is useful to binutils also. */
extern const struct demangler_engine
{
const char *const demangling_style_name;
const enum demangling_styles demangling_style;
const char *const demangling_style_doc;
} libiberty_demanglers[];
extern char *
cplus_demangle (const char *mangled, int options);
extern int
cplus_demangle_opname (const char *opname, char *result, int options);
extern const char *
cplus_mangle_opname (const char *opname, int options);
/* Note: This sets global state. FIXME if you care about multi-threading. */
extern void
set_cplus_marker_for_demangling (int ch);
extern enum demangling_styles
cplus_demangle_set_style (enum demangling_styles style);
extern enum demangling_styles
cplus_demangle_name_to_style (const char *name);
/* Callback typedef for allocation-less demangler interfaces. */
typedef void (*demangle_callbackref) (const char *, size_t, void *);
/* V3 ABI demangling entry points, defined in cp-demangle.c. Callback
variants return non-zero on success, zero on error. char* variants
return a string allocated by malloc on success, NULL on error. */
extern int
cplus_demangle_v3_callback (const char *mangled, int options,
demangle_callbackref callback, void *opaque);
extern char*
cplus_demangle_v3 (const char *mangled, int options);
extern int
java_demangle_v3_callback (const char *mangled,
demangle_callbackref callback, void *opaque);
extern char*
java_demangle_v3 (const char *mangled);
char *
ada_demangle (const char *mangled, int options);
enum gnu_v3_ctor_kinds {
gnu_v3_complete_object_ctor = 1,
gnu_v3_base_object_ctor,
gnu_v3_complete_object_allocating_ctor,
gnu_v3_object_ctor_group
};
/* Return non-zero iff NAME is the mangled form of a constructor name
in the G++ V3 ABI demangling style. Specifically, return an `enum
gnu_v3_ctor_kinds' value indicating what kind of constructor
it is. */
extern enum gnu_v3_ctor_kinds
is_gnu_v3_mangled_ctor (const char *name);
enum gnu_v3_dtor_kinds {
gnu_v3_deleting_dtor = 1,
gnu_v3_complete_object_dtor,
gnu_v3_base_object_dtor,
gnu_v3_object_dtor_group
};
/* Return non-zero iff NAME is the mangled form of a destructor name
in the G++ V3 ABI demangling style. Specifically, return an `enum
gnu_v3_dtor_kinds' value, indicating what kind of destructor
it is. */
extern enum gnu_v3_dtor_kinds
is_gnu_v3_mangled_dtor (const char *name);
/* The V3 demangler works in two passes. The first pass builds a tree
representation of the mangled name, and the second pass turns the
tree representation into a demangled string. Here we define an
interface to permit a caller to build their own tree
representation, which they can pass to the demangler to get a
demangled string. This can be used to canonicalize user input into
something which the demangler might output. It could also be used
by other demanglers in the future. */
/* These are the component types which may be found in the tree. Many
component types have one or two subtrees, referred to as left and
right (a component type with only one subtree puts it in the left
subtree). */
enum demangle_component_type
{
/* A name, with a length and a pointer to a string. */
DEMANGLE_COMPONENT_NAME,
/* A qualified name. The left subtree is a class or namespace or
some such thing, and the right subtree is a name qualified by
that class. */
DEMANGLE_COMPONENT_QUAL_NAME,
/* A local name. The left subtree describes a function, and the
right subtree is a name which is local to that function. */
DEMANGLE_COMPONENT_LOCAL_NAME,
/* A typed name. The left subtree is a name, and the right subtree
describes that name as a function. */
DEMANGLE_COMPONENT_TYPED_NAME,
/* A template. The left subtree is a template name, and the right
subtree is a template argument list. */
DEMANGLE_COMPONENT_TEMPLATE,
/* A template parameter. This holds a number, which is the template
parameter index. */
DEMANGLE_COMPONENT_TEMPLATE_PARAM,
/* A function parameter. This holds a number, which is the index. */
DEMANGLE_COMPONENT_FUNCTION_PARAM,
/* A constructor. This holds a name and the kind of
constructor. */
DEMANGLE_COMPONENT_CTOR,
/* A destructor. This holds a name and the kind of destructor. */
DEMANGLE_COMPONENT_DTOR,
/* A vtable. This has one subtree, the type for which this is a
vtable. */
DEMANGLE_COMPONENT_VTABLE,
/* A VTT structure. This has one subtree, the type for which this
is a VTT. */
DEMANGLE_COMPONENT_VTT,
/* A construction vtable. The left subtree is the type for which
this is a vtable, and the right subtree is the derived type for
which this vtable is built. */
DEMANGLE_COMPONENT_CONSTRUCTION_VTABLE,
/* A typeinfo structure. This has one subtree, the type for which
this is the tpeinfo structure. */
DEMANGLE_COMPONENT_TYPEINFO,
/* A typeinfo name. This has one subtree, the type for which this
is the typeinfo name. */
DEMANGLE_COMPONENT_TYPEINFO_NAME,
/* A typeinfo function. This has one subtree, the type for which
this is the tpyeinfo function. */
DEMANGLE_COMPONENT_TYPEINFO_FN,
/* A thunk. This has one subtree, the name for which this is a
thunk. */
DEMANGLE_COMPONENT_THUNK,
/* A virtual thunk. This has one subtree, the name for which this
is a virtual thunk. */
DEMANGLE_COMPONENT_VIRTUAL_THUNK,
/* A covariant thunk. This has one subtree, the name for which this
is a covariant thunk. */
DEMANGLE_COMPONENT_COVARIANT_THUNK,
/* A Java class. This has one subtree, the type. */
DEMANGLE_COMPONENT_JAVA_CLASS,
/* A guard variable. This has one subtree, the name for which this
is a guard variable. */
DEMANGLE_COMPONENT_GUARD,
/* The init and wrapper functions for C++11 thread_local variables. */
DEMANGLE_COMPONENT_TLS_INIT,
DEMANGLE_COMPONENT_TLS_WRAPPER,
/* A reference temporary. This has one subtree, the name for which
this is a temporary. */
DEMANGLE_COMPONENT_REFTEMP,
/* A hidden alias. This has one subtree, the encoding for which it
is providing alternative linkage. */
DEMANGLE_COMPONENT_HIDDEN_ALIAS,
/* A standard substitution. This holds the name of the
substitution. */
DEMANGLE_COMPONENT_SUB_STD,
/* The restrict qualifier. The one subtree is the type which is
being qualified. */
DEMANGLE_COMPONENT_RESTRICT,
/* The volatile qualifier. The one subtree is the type which is
being qualified. */
DEMANGLE_COMPONENT_VOLATILE,
/* The const qualifier. The one subtree is the type which is being
qualified. */
DEMANGLE_COMPONENT_CONST,
/* The restrict qualifier modifying a member function. The one
subtree is the type which is being qualified. */
DEMANGLE_COMPONENT_RESTRICT_THIS,
/* The volatile qualifier modifying a member function. The one
subtree is the type which is being qualified. */
DEMANGLE_COMPONENT_VOLATILE_THIS,
/* The const qualifier modifying a member function. The one subtree
is the type which is being qualified. */
DEMANGLE_COMPONENT_CONST_THIS,
/* C++11 A reference modifying a member function. The one subtree is the
type which is being referenced. */
DEMANGLE_COMPONENT_REFERENCE_THIS,
/* C++11: An rvalue reference modifying a member function. The one
subtree is the type which is being referenced. */
DEMANGLE_COMPONENT_RVALUE_REFERENCE_THIS,
/* A vendor qualifier. The left subtree is the type which is being
qualified, and the right subtree is the name of the
qualifier. */
DEMANGLE_COMPONENT_VENDOR_TYPE_QUAL,
/* A pointer. The one subtree is the type which is being pointed
to. */
DEMANGLE_COMPONENT_POINTER,
/* A reference. The one subtree is the type which is being
referenced. */
DEMANGLE_COMPONENT_REFERENCE,
/* C++0x: An rvalue reference. The one subtree is the type which is
being referenced. */
DEMANGLE_COMPONENT_RVALUE_REFERENCE,
/* A complex type. The one subtree is the base type. */
DEMANGLE_COMPONENT_COMPLEX,
/* An imaginary type. The one subtree is the base type. */
DEMANGLE_COMPONENT_IMAGINARY,
/* A builtin type. This holds the builtin type information. */
DEMANGLE_COMPONENT_BUILTIN_TYPE,
/* A vendor's builtin type. This holds the name of the type. */
DEMANGLE_COMPONENT_VENDOR_TYPE,
/* A function type. The left subtree is the return type. The right
subtree is a list of ARGLIST nodes. Either or both may be
NULL. */
DEMANGLE_COMPONENT_FUNCTION_TYPE,
/* An array type. The left subtree is the dimension, which may be
NULL, or a string (represented as DEMANGLE_COMPONENT_NAME), or an
expression. The right subtree is the element type. */
DEMANGLE_COMPONENT_ARRAY_TYPE,
/* A pointer to member type. The left subtree is the class type,
and the right subtree is the member type. CV-qualifiers appear
on the latter. */
DEMANGLE_COMPONENT_PTRMEM_TYPE,
/* A fixed-point type. */
DEMANGLE_COMPONENT_FIXED_TYPE,
/* A vector type. The left subtree is the number of elements,
the right subtree is the element type. */
DEMANGLE_COMPONENT_VECTOR_TYPE,
/* An argument list. The left subtree is the current argument, and
the right subtree is either NULL or another ARGLIST node. */
DEMANGLE_COMPONENT_ARGLIST,
/* A template argument list. The left subtree is the current
template argument, and the right subtree is either NULL or
another TEMPLATE_ARGLIST node. */
DEMANGLE_COMPONENT_TEMPLATE_ARGLIST,
/* An initializer list. The left subtree is either an explicit type or
NULL, and the right subtree is a DEMANGLE_COMPONENT_ARGLIST. */
DEMANGLE_COMPONENT_INITIALIZER_LIST,
/* An operator. This holds information about a standard
operator. */
DEMANGLE_COMPONENT_OPERATOR,
/* An extended operator. This holds the number of arguments, and
the name of the extended operator. */
DEMANGLE_COMPONENT_EXTENDED_OPERATOR,
/* A typecast, represented as a unary operator. The one subtree is
the type to which the argument should be cast. */
DEMANGLE_COMPONENT_CAST,
/* A nullary expression. The left subtree is the operator. */
DEMANGLE_COMPONENT_NULLARY,
/* A unary expression. The left subtree is the operator, and the
right subtree is the single argument. */
DEMANGLE_COMPONENT_UNARY,
/* A binary expression. The left subtree is the operator, and the
right subtree is a BINARY_ARGS. */
DEMANGLE_COMPONENT_BINARY,
/* Arguments to a binary expression. The left subtree is the first
argument, and the right subtree is the second argument. */
DEMANGLE_COMPONENT_BINARY_ARGS,
/* A trinary expression. The left subtree is the operator, and the
right subtree is a TRINARY_ARG1. */
DEMANGLE_COMPONENT_TRINARY,
/* Arguments to a trinary expression. The left subtree is the first
argument, and the right subtree is a TRINARY_ARG2. */
DEMANGLE_COMPONENT_TRINARY_ARG1,
/* More arguments to a trinary expression. The left subtree is the
second argument, and the right subtree is the third argument. */
DEMANGLE_COMPONENT_TRINARY_ARG2,
/* A literal. The left subtree is the type, and the right subtree
is the value, represented as a DEMANGLE_COMPONENT_NAME. */
DEMANGLE_COMPONENT_LITERAL,
/* A negative literal. Like LITERAL, but the value is negated.
This is a minor hack: the NAME used for LITERAL points directly
to the mangled string, but since negative numbers are mangled
using 'n' instead of '-', we want a way to indicate a negative
number which involves neither modifying the mangled string nor
allocating a new copy of the literal in memory. */
DEMANGLE_COMPONENT_LITERAL_NEG,
/* A libgcj compiled resource. The left subtree is the name of the
resource. */
DEMANGLE_COMPONENT_JAVA_RESOURCE,
/* A name formed by the concatenation of two parts. The left
subtree is the first part and the right subtree the second. */
DEMANGLE_COMPONENT_COMPOUND_NAME,
/* A name formed by a single character. */
DEMANGLE_COMPONENT_CHARACTER,
/* A number. */
DEMANGLE_COMPONENT_NUMBER,
/* A decltype type. */
DEMANGLE_COMPONENT_DECLTYPE,
/* Global constructors keyed to name. */
DEMANGLE_COMPONENT_GLOBAL_CONSTRUCTORS,
/* Global destructors keyed to name. */
DEMANGLE_COMPONENT_GLOBAL_DESTRUCTORS,
/* A lambda closure type. */
DEMANGLE_COMPONENT_LAMBDA,
/* A default argument scope. */
DEMANGLE_COMPONENT_DEFAULT_ARG,
/* An unnamed type. */
DEMANGLE_COMPONENT_UNNAMED_TYPE,
/* A transactional clone. This has one subtree, the encoding for
which it is providing alternative linkage. */
DEMANGLE_COMPONENT_TRANSACTION_CLONE,
/* A non-transactional clone entry point. In the i386/x86_64 abi,
the unmangled symbol of a tm_callable becomes a thunk and the
non-transactional function version is mangled thus. */
DEMANGLE_COMPONENT_NONTRANSACTION_CLONE,
/* A pack expansion. */
DEMANGLE_COMPONENT_PACK_EXPANSION,
/* A name with an ABI tag. */
DEMANGLE_COMPONENT_TAGGED_NAME,
/* A cloned function. */
DEMANGLE_COMPONENT_CLONE
};
/* Types which are only used internally. */
struct demangle_operator_info;
struct demangle_builtin_type_info;
/* A node in the tree representation is an instance of a struct
demangle_component. Note that the field names of the struct are
not well protected against macros defined by the file including
this one. We can fix this if it ever becomes a problem. */
struct demangle_component
{
/* The type of this component. */
enum demangle_component_type type;
union
{
/* For DEMANGLE_COMPONENT_NAME. */
struct
{
/* A pointer to the name (which need not NULL terminated) and
its length. */
const char *s;
int len;
} s_name;
/* For DEMANGLE_COMPONENT_OPERATOR. */
struct
{
/* Operator. */
const struct demangle_operator_info *op;
} s_operator;
/* For DEMANGLE_COMPONENT_EXTENDED_OPERATOR. */
struct
{
/* Number of arguments. */
int args;
/* Name. */
struct demangle_component *name;
} s_extended_operator;
/* For DEMANGLE_COMPONENT_FIXED_TYPE. */
struct
{
/* The length, indicated by a C integer type name. */
struct demangle_component *length;
/* _Accum or _Fract? */
short accum;
/* Saturating or not? */
short sat;
} s_fixed;
/* For DEMANGLE_COMPONENT_CTOR. */
struct
{
/* Kind of constructor. */
enum gnu_v3_ctor_kinds kind;
/* Name. */
struct demangle_component *name;
} s_ctor;
/* For DEMANGLE_COMPONENT_DTOR. */
struct
{
/* Kind of destructor. */
enum gnu_v3_dtor_kinds kind;
/* Name. */
struct demangle_component *name;
} s_dtor;
/* For DEMANGLE_COMPONENT_BUILTIN_TYPE. */
struct
{
/* Builtin type. */
const struct demangle_builtin_type_info *type;
} s_builtin;
/* For DEMANGLE_COMPONENT_SUB_STD. */
struct
{
/* Standard substitution string. */
const char* string;
/* Length of string. */
int len;
} s_string;
/* For DEMANGLE_COMPONENT_*_PARAM. */
struct
{
/* Parameter index. */
long number;
} s_number;
/* For DEMANGLE_COMPONENT_CHARACTER. */
struct
{
int character;
} s_character;
/* For other types. */
struct
{
/* Left (or only) subtree. */
struct demangle_component *left;
/* Right subtree. */
struct demangle_component *right;
} s_binary;
struct
{
/* subtree, same place as d_left. */
struct demangle_component *sub;
/* integer. */
int num;
} s_unary_num;
} u;
};
/* People building mangled trees are expected to allocate instances of
struct demangle_component themselves. They can then call one of
the following functions to fill them in. */
/* Fill in most component types with a left subtree and a right
subtree. Returns non-zero on success, zero on failure, such as an
unrecognized or inappropriate component type. */
extern int
cplus_demangle_fill_component (struct demangle_component *fill,
enum demangle_component_type,
struct demangle_component *left,
struct demangle_component *right);
/* Fill in a DEMANGLE_COMPONENT_NAME. Returns non-zero on success,
zero for bad arguments. */
extern int
cplus_demangle_fill_name (struct demangle_component *fill,
const char *, int);
/* Fill in a DEMANGLE_COMPONENT_BUILTIN_TYPE, using the name of the
builtin type (e.g., "int", etc.). Returns non-zero on success,
zero if the type is not recognized. */
extern int
cplus_demangle_fill_builtin_type (struct demangle_component *fill,
const char *type_name);
/* Fill in a DEMANGLE_COMPONENT_OPERATOR, using the name of the
operator and the number of arguments which it takes (the latter is
used to disambiguate operators which can be both binary and unary,
such as '-'). Returns non-zero on success, zero if the operator is
not recognized. */
extern int
cplus_demangle_fill_operator (struct demangle_component *fill,
const char *opname, int args);
/* Fill in a DEMANGLE_COMPONENT_EXTENDED_OPERATOR, providing the
number of arguments and the name. Returns non-zero on success,
zero for bad arguments. */
extern int
cplus_demangle_fill_extended_operator (struct demangle_component *fill,
int numargs,
struct demangle_component *nm);
/* Fill in a DEMANGLE_COMPONENT_CTOR. Returns non-zero on success,
zero for bad arguments. */
extern int
cplus_demangle_fill_ctor (struct demangle_component *fill,
enum gnu_v3_ctor_kinds kind,
struct demangle_component *name);
/* Fill in a DEMANGLE_COMPONENT_DTOR. Returns non-zero on success,
zero for bad arguments. */
extern int
cplus_demangle_fill_dtor (struct demangle_component *fill,
enum gnu_v3_dtor_kinds kind,
struct demangle_component *name);
/* This function translates a mangled name into a struct
demangle_component tree. The first argument is the mangled name.
The second argument is DMGL_* options. This returns a pointer to a
tree on success, or NULL on failure. On success, the third
argument is set to a block of memory allocated by malloc. This
block should be passed to free when the tree is no longer
needed. */
extern struct demangle_component *
cplus_demangle_v3_components (const char *mangled, int options, void **mem);
/* This function takes a struct demangle_component tree and returns
the corresponding demangled string. The first argument is DMGL_*
options. The second is the tree to demangle. The third is a guess
at the length of the demangled string, used to initially allocate
the return buffer. The fourth is a pointer to a size_t. On
success, this function returns a buffer allocated by malloc(), and
sets the size_t pointed to by the fourth argument to the size of
the allocated buffer (not the length of the returned string). On
failure, this function returns NULL, and sets the size_t pointed to
by the fourth argument to 0 for an invalid tree, or to 1 for a
memory allocation error. */
extern char *
cplus_demangle_print (int options,
const struct demangle_component *tree,
int estimated_length,
size_t *p_allocated_size);
/* This function takes a struct demangle_component tree and passes back
a demangled string in one or more calls to a callback function.
The first argument is DMGL_* options. The second is the tree to
demangle. The third is a pointer to a callback function; on each call
this receives an element of the demangled string, its length, and an
opaque value. The fourth is the opaque value passed to the callback.
The callback is called once or more to return the full demangled
string. The demangled element string is always nul-terminated, though
its length is also provided for convenience. In contrast to
cplus_demangle_print(), this function does not allocate heap memory
to grow output strings (except perhaps where alloca() is implemented
by malloc()), and so is normally safe for use where the heap has been
corrupted. On success, this function returns 1; on failure, 0. */
extern int
cplus_demangle_print_callback (int options,
const struct demangle_component *tree,
demangle_callbackref callback, void *opaque);
#ifdef __cplusplus
}
#endif /* __cplusplus */
#endif /* DEMANGLE_H */

View file

@ -0,0 +1,77 @@
/* ###
* IP: GPL 3
* REVIEWED: YES
*/
/* An abstract string datatype.
Copyright (C) 1998, 1999, 2000, 2002, 2004, 2005, 2009
Free Software Foundation, Inc.
Contributed by Mark Mitchell (mark@markmitchell.com).
This file is part of GCC.
GCC 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.
GCC 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 GCC; see the file COPYING. If not, write to
the Free Software Foundation, 51 Franklin Street - Fifth Floor,
Boston, MA 02110-1301, USA. */
#ifndef DYN_STRING_H
#define DYN_STRING_H
#ifdef __cplusplus
extern "C" {
#endif
typedef struct dyn_string
{
int allocated; /* The amount of space allocated for the string. */
int length; /* The actual length of the string. */
char *s; /* The string itself, NUL-terminated. */
}* dyn_string_t;
/* The length STR, in bytes, not including the terminating NUL. */
#define dyn_string_length(STR) \
((STR)->length)
/* The NTBS in which the contents of STR are stored. */
#define dyn_string_buf(STR) \
((STR)->s)
/* Compare DS1 to DS2 with strcmp. */
#define dyn_string_compare(DS1, DS2) \
(strcmp ((DS1)->s, (DS2)->s))
extern int dyn_string_init (struct dyn_string *, int);
extern dyn_string_t dyn_string_new (int);
extern void dyn_string_delete (dyn_string_t);
extern char *dyn_string_release (dyn_string_t);
extern dyn_string_t dyn_string_resize (dyn_string_t, int);
extern void dyn_string_clear (dyn_string_t);
extern int dyn_string_copy (dyn_string_t, dyn_string_t);
extern int dyn_string_copy_cstr (dyn_string_t, const char *);
extern int dyn_string_prepend (dyn_string_t, dyn_string_t);
extern int dyn_string_prepend_cstr (dyn_string_t, const char *);
extern int dyn_string_insert (dyn_string_t, int, dyn_string_t);
extern int dyn_string_insert_cstr (dyn_string_t, int, const char *);
extern int dyn_string_insert_char (dyn_string_t, int, int);
extern int dyn_string_append (dyn_string_t, dyn_string_t);
extern int dyn_string_append_cstr (dyn_string_t, const char *);
extern int dyn_string_append_char (dyn_string_t, int);
extern int dyn_string_substring (dyn_string_t, dyn_string_t, int, int);
extern int dyn_string_eq (dyn_string_t, dyn_string_t);
#ifdef __cplusplus
}
#endif
#endif /* !defined (DYN_STRING_H) */

View file

@ -0,0 +1,148 @@
/* ###
* IP: GPL 3
* REVIEWED: YES
*/
/* Declarations for getopt.
Copyright 1989, 1990, 1991, 1992, 1993, 1994, 1996, 1997, 1998, 2000,
2002 Free Software Foundation, Inc.
NOTE: The canonical source of this file is maintained with the GNU C Library.
Bugs can be reported to bug-glibc@gnu.org.
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, write to the Free Software
Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301,
USA. */
#ifndef _GETOPT_H
#define _GETOPT_H 1
#ifdef __cplusplus
extern "C" {
#endif
/* For communication from `getopt' to the caller.
When `getopt' finds an option that takes an argument,
the argument value is returned here.
Also, when `ordering' is RETURN_IN_ORDER,
each non-option ARGV-element is returned here. */
extern char *optarg;
/* Index in ARGV of the next element to be scanned.
This is used for communication to and from the caller
and for communication between successive calls to `getopt'.
On entry to `getopt', zero means this is the first call; initialize.
When `getopt' returns -1, this is the index of the first of the
non-option elements that the caller should itself scan.
Otherwise, `optind' communicates from one call to the next
how much of ARGV has been scanned so far. */
extern int optind;
/* Callers store zero here to inhibit the error message `getopt' prints
for unrecognized options. */
extern int opterr;
/* Set to an option character which was unrecognized. */
extern int optopt;
/* Describe the long-named options requested by the application.
The LONG_OPTIONS argument to getopt_long or getopt_long_only is a vector
of `struct option' terminated by an element containing a name which is
zero.
The field `has_arg' is:
no_argument (or 0) if the option does not take an argument,
required_argument (or 1) if the option requires an argument,
optional_argument (or 2) if the option takes an optional argument.
If the field `flag' is not NULL, it points to a variable that is set
to the value given in the field `val' when the option is found, but
left unchanged if the option is not found.
To have a long-named option do something other than set an `int' to
a compiled-in constant, such as set a value from `optarg', set the
option's `flag' field to zero and its `val' field to a nonzero
value (the equivalent single-letter option character, if there is
one). For long options that have a zero `flag' field, `getopt'
returns the contents of the `val' field. */
struct option
{
#if defined (__STDC__) && __STDC__
const char *name;
#else
char *name;
#endif
/* has_arg can't be an enum because some compilers complain about
type mismatches in all the code that assumes it is an int. */
int has_arg;
int *flag;
int val;
};
/* Names for the values of the `has_arg' field of `struct option'. */
#define no_argument 0
#define required_argument 1
#define optional_argument 2
#if defined (__STDC__) && __STDC__
/* HAVE_DECL_* is a three-state macro: undefined, 0 or 1. If it is
undefined, we haven't run the autoconf check so provide the
declaration without arguments. If it is 0, we checked and failed
to find the declaration so provide a fully prototyped one. If it
is 1, we found it so don't provide any declaration at all. */
#if !HAVE_DECL_GETOPT
#if defined (__GNU_LIBRARY__) || defined (HAVE_DECL_GETOPT)
/* Many other libraries have conflicting prototypes for getopt, with
differences in the consts, in unistd.h. To avoid compilation
errors, only prototype getopt for the GNU C library. */
extern int getopt (int argc, char *const *argv, const char *shortopts);
#else
#ifndef __cplusplus
extern int getopt ();
#endif /* __cplusplus */
#endif
#endif /* !HAVE_DECL_GETOPT */
extern int getopt_long (int argc, char *const *argv, const char *shortopts,
const struct option *longopts, int *longind);
extern int getopt_long_only (int argc, char *const *argv,
const char *shortopts,
const struct option *longopts, int *longind);
/* Internal only. Users should not call this directly. */
extern int _getopt_internal (int argc, char *const *argv,
const char *shortopts,
const struct option *longopts, int *longind,
int long_only);
#else /* not __STDC__ */
extern int getopt ();
extern int getopt_long ();
extern int getopt_long_only ();
extern int _getopt_internal ();
#endif /* __STDC__ */
#ifdef __cplusplus
}
#endif
#endif /* getopt.h */

View file

@ -0,0 +1,690 @@
/* ###
* IP: GPL 3
* REVIEWED: YES
*/
/* Function declarations for libiberty.
Copyright 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005,
2006, 2007, 2008, 2009, 2010, 2011 Free Software Foundation, Inc.
Note - certain prototypes declared in this header file are for
functions whoes implementation copyright does not belong to the
FSF. Those prototypes are present in this file for reference
purposes only and their presence in this file should not construed
as an indication of ownership by the FSF of the implementation of
those functions in any way or form whatsoever.
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, write to the Free Software
Foundation, Inc., 51 Franklin Street - Fifth Floor,
Boston, MA 02110-1301, USA.
Written by Cygnus Support, 1994.
The libiberty library provides a number of functions which are
missing on some operating systems. We do not declare those here,
to avoid conflicts with the system header files on operating
systems that do support those functions. In this file we only
declare those functions which are specific to libiberty. */
#ifndef LIBIBERTY_H
#define LIBIBERTY_H
#ifdef __cplusplus
extern "C" {
#endif
#include "ansidecl.h"
/* Get a definition for size_t. */
#include <stddef.h>
/* Get a definition for va_list. */
#include <stdarg.h>
#include <stdio.h>
/* If the OS supports it, ensure that the supplied stream is setup to
avoid any multi-threaded locking. Otherwise leave the FILE pointer
unchanged. If the stream is NULL do nothing. */
extern void unlock_stream (FILE *);
/* If the OS supports it, ensure that the standard I/O streams, stdin,
stdout and stderr are setup to avoid any multi-threaded locking.
Otherwise do nothing. */
extern void unlock_std_streams (void);
/* Open and return a FILE pointer. If the OS supports it, ensure that
the stream is setup to avoid any multi-threaded locking. Otherwise
return the FILE pointer unchanged. */
extern FILE *fopen_unlocked (const char *, const char *);
extern FILE *fdopen_unlocked (int, const char *);
extern FILE *freopen_unlocked (const char *, const char *, FILE *);
/* Build an argument vector from a string. Allocates memory using
malloc. Use freeargv to free the vector. */
extern char **buildargv (const char *) ATTRIBUTE_MALLOC;
/* Free a vector returned by buildargv. */
extern void freeargv (char **);
/* Duplicate an argument vector. Allocates memory using malloc. Use
freeargv to free the vector. */
extern char **dupargv (char **) ATTRIBUTE_MALLOC;
/* Expand "@file" arguments in argv. */
extern void expandargv PARAMS ((int *, char ***));
/* Write argv to an @-file, inserting necessary quoting. */
extern int writeargv PARAMS ((char **, FILE *));
/* Return the number of elements in argv. */
extern int countargv (char**);
/* Return the last component of a path name. Note that we can't use a
prototype here because the parameter is declared inconsistently
across different systems, sometimes as "char *" and sometimes as
"const char *" */
/* HAVE_DECL_* is a three-state macro: undefined, 0 or 1. If it is
undefined, we haven't run the autoconf check so provide the
declaration without arguments. If it is 0, we checked and failed
to find the declaration so provide a fully prototyped one. If it
is 1, we found it so don't provide any declaration at all. */
#if !HAVE_DECL_BASENAME
#if defined (__GNU_LIBRARY__ ) || defined (__linux__) || defined (__FreeBSD__) || defined (__OpenBSD__) || defined(__NetBSD__) || defined (__CYGWIN__) || defined (__CYGWIN32__) || defined (__MINGW32__) || defined (HAVE_DECL_BASENAME)
extern char *basename (const char *);
#else
/* Do not allow basename to be used if there is no prototype seen. We
either need to use the above prototype or have one from
autoconf which would result in HAVE_DECL_BASENAME being set. */
#define basename basename_cannot_be_used_without_a_prototype
#endif
#endif
/* A well-defined basename () that is always compiled in. */
extern const char *lbasename (const char *);
/* Same, but assumes DOS semantics (drive name, backslash is also a
dir separator) regardless of host. */
extern const char *dos_lbasename (const char *);
/* Same, but assumes Unix semantics (absolute paths always start with
a slash, only forward slash is accepted as dir separator)
regardless of host. */
extern const char *unix_lbasename (const char *);
/* A well-defined realpath () that is always compiled in. */
extern char *lrealpath (const char *);
/* Concatenate an arbitrary number of strings. You must pass NULL as
the last argument of this function, to terminate the list of
strings. Allocates memory using xmalloc. */
extern char *concat (const char *, ...) ATTRIBUTE_MALLOC ATTRIBUTE_SENTINEL;
/* Concatenate an arbitrary number of strings. You must pass NULL as
the last argument of this function, to terminate the list of
strings. Allocates memory using xmalloc. The first argument is
not one of the strings to be concatenated, but if not NULL is a
pointer to be freed after the new string is created, similar to the
way xrealloc works. */
extern char *reconcat (char *, const char *, ...) ATTRIBUTE_MALLOC ATTRIBUTE_SENTINEL;
/* Determine the length of concatenating an arbitrary number of
strings. You must pass NULL as the last argument of this function,
to terminate the list of strings. */
extern unsigned long concat_length (const char *, ...) ATTRIBUTE_SENTINEL;
/* Concatenate an arbitrary number of strings into a SUPPLIED area of
memory. You must pass NULL as the last argument of this function,
to terminate the list of strings. The supplied memory is assumed
to be large enough. */
extern char *concat_copy (char *, const char *, ...) ATTRIBUTE_SENTINEL;
/* Concatenate an arbitrary number of strings into a GLOBAL area of
memory. You must pass NULL as the last argument of this function,
to terminate the list of strings. The supplied memory is assumed
to be large enough. */
extern char *concat_copy2 (const char *, ...) ATTRIBUTE_SENTINEL;
/* This is the global area used by concat_copy2. */
extern char *libiberty_concat_ptr;
/* Concatenate an arbitrary number of strings. You must pass NULL as
the last argument of this function, to terminate the list of
strings. Allocates memory using alloca. The arguments are
evaluated twice! */
#define ACONCAT(ACONCAT_PARAMS) \
(libiberty_concat_ptr = (char *) alloca (concat_length ACONCAT_PARAMS + 1), \
concat_copy2 ACONCAT_PARAMS)
/* Check whether two file descriptors refer to the same file. */
extern int fdmatch (int fd1, int fd2);
/* Return the position of the first bit set in the argument. */
/* Prototypes vary from system to system, so we only provide a
prototype on systems where we know that we need it. */
#if defined (HAVE_DECL_FFS) && !HAVE_DECL_FFS
extern int ffs(int);
#endif
/* Get the working directory. The result is cached, so don't call
chdir() between calls to getpwd(). */
extern char * getpwd (void);
/* Get the current time. */
/* Prototypes vary from system to system, so we only provide a
prototype on systems where we know that we need it. */
#ifdef __MINGW32__
/* Forward declaration to avoid #include <sys/time.h>. */
struct timeval;
extern int gettimeofday (struct timeval *, void *);
#endif
/* Get the amount of time the process has run, in microseconds. */
extern long get_run_time (void);
/* Generate a relocated path to some installation directory. Allocates
return value using malloc. */
extern char *make_relative_prefix (const char *, const char *,
const char *) ATTRIBUTE_MALLOC;
/* Generate a relocated path to some installation directory without
attempting to follow any soft links. Allocates
return value using malloc. */
extern char *make_relative_prefix_ignore_links (const char *, const char *,
const char *) ATTRIBUTE_MALLOC;
/* Choose a temporary directory to use for scratch files. */
extern char *choose_temp_base (void) ATTRIBUTE_MALLOC;
/* Return a temporary file name or NULL if unable to create one. */
extern char *make_temp_file (const char *) ATTRIBUTE_MALLOC;
/* Remove a link to a file unless it is special. */
extern int unlink_if_ordinary (const char *);
/* Allocate memory filled with spaces. Allocates using malloc. */
extern const char *spaces (int count);
/* Return the maximum error number for which strerror will return a
string. */
extern int errno_max (void);
/* Return the name of an errno value (e.g., strerrno (EINVAL) returns
"EINVAL"). */
extern const char *strerrno (int);
/* Given the name of an errno value, return the value. */
extern int strtoerrno (const char *);
/* ANSI's strerror(), but more robust. */
extern char *xstrerror (int);
/* Return the maximum signal number for which strsignal will return a
string. */
extern int signo_max (void);
/* Return a signal message string for a signal number
(e.g., strsignal (SIGHUP) returns something like "Hangup"). */
/* This is commented out as it can conflict with one in system headers.
We still document its existence though. */
/*extern const char *strsignal (int);*/
/* Return the name of a signal number (e.g., strsigno (SIGHUP) returns
"SIGHUP"). */
extern const char *strsigno (int);
/* Given the name of a signal, return its number. */
extern int strtosigno (const char *);
/* Register a function to be run by xexit. Returns 0 on success. */
extern int xatexit (void (*fn) (void));
/* Exit, calling all the functions registered with xatexit. */
extern void xexit (int status) ATTRIBUTE_NORETURN;
/* Set the program name used by xmalloc. */
extern void xmalloc_set_program_name (const char *);
/* Report an allocation failure. */
extern void xmalloc_failed (size_t) ATTRIBUTE_NORETURN;
/* Allocate memory without fail. If malloc fails, this will print a
message to stderr (using the name set by xmalloc_set_program_name,
if any) and then call xexit. */
extern void *xmalloc (size_t) ATTRIBUTE_MALLOC;
/* Reallocate memory without fail. This works like xmalloc. Note,
realloc type functions are not suitable for attribute malloc since
they may return the same address across multiple calls. */
extern void *xrealloc (void *, size_t);
/* Allocate memory without fail and set it to zero. This works like
xmalloc. */
extern void *xcalloc (size_t, size_t) ATTRIBUTE_MALLOC;
/* Copy a string into a memory buffer without fail. */
extern char *xstrdup (const char *) ATTRIBUTE_MALLOC;
/* Copy at most N characters from string into a buffer without fail. */
extern char *xstrndup (const char *, size_t) ATTRIBUTE_MALLOC;
/* Copy an existing memory buffer to a new memory buffer without fail. */
extern void *xmemdup (const void *, size_t, size_t) ATTRIBUTE_MALLOC;
/* Physical memory routines. Return values are in BYTES. */
extern double physmem_total (void);
extern double physmem_available (void);
/* Compute the 32-bit CRC of a block of memory. */
extern unsigned int xcrc32 (const unsigned char *, int, unsigned int);
/* These macros provide a K&R/C89/C++-friendly way of allocating structures
with nice encapsulation. The XDELETE*() macros are technically
superfluous, but provided here for symmetry. Using them consistently
makes it easier to update client code to use different allocators such
as new/delete and new[]/delete[]. */
/* Scalar allocators. */
#define XALLOCA(T) ((T *) alloca (sizeof (T)))
#define XNEW(T) ((T *) xmalloc (sizeof (T)))
#define XCNEW(T) ((T *) xcalloc (1, sizeof (T)))
#define XDUP(T, P) ((T *) xmemdup ((P), sizeof (T), sizeof (T)))
#define XDELETE(P) free ((void*) (P))
/* Array allocators. */
#define XALLOCAVEC(T, N) ((T *) alloca (sizeof (T) * (N)))
#define XNEWVEC(T, N) ((T *) xmalloc (sizeof (T) * (N)))
#define XCNEWVEC(T, N) ((T *) xcalloc ((N), sizeof (T)))
#define XDUPVEC(T, P, N) ((T *) xmemdup ((P), sizeof (T) * (N), sizeof (T) * (N)))
#define XRESIZEVEC(T, P, N) ((T *) xrealloc ((void *) (P), sizeof (T) * (N)))
#define XDELETEVEC(P) free ((void*) (P))
/* Allocators for variable-sized structures and raw buffers. */
#define XALLOCAVAR(T, S) ((T *) alloca ((S)))
#define XNEWVAR(T, S) ((T *) xmalloc ((S)))
#define XCNEWVAR(T, S) ((T *) xcalloc (1, (S)))
#define XDUPVAR(T, P, S1, S2) ((T *) xmemdup ((P), (S1), (S2)))
#define XRESIZEVAR(T, P, S) ((T *) xrealloc ((P), (S)))
/* Type-safe obstack allocator. */
#define XOBNEW(O, T) ((T *) obstack_alloc ((O), sizeof (T)))
#define XOBNEWVEC(O, T, N) ((T *) obstack_alloc ((O), sizeof (T) * (N)))
#define XOBNEWVAR(O, T, S) ((T *) obstack_alloc ((O), (S)))
#define XOBFINISH(O, T) ((T) obstack_finish ((O)))
/* hex character manipulation routines */
#define _hex_array_size 256
#define _hex_bad 99
extern const unsigned char _hex_value[_hex_array_size];
extern void hex_init (void);
#define hex_p(c) (hex_value (c) != _hex_bad)
/* If you change this, note well: Some code relies on side effects in
the argument being performed exactly once. */
#define hex_value(c) ((unsigned int) _hex_value[(unsigned char) (c)])
/* Flags for pex_init. These are bits to be or'ed together. */
/* Record subprocess times, if possible. */
#define PEX_RECORD_TIMES 0x1
/* Use pipes for communication between processes, if possible. */
#define PEX_USE_PIPES 0x2
/* Save files used for communication between processes. */
#define PEX_SAVE_TEMPS 0x4
/* Prepare to execute one or more programs, with standard output of
each program fed to standard input of the next.
FLAGS As above.
PNAME The name of the program to report in error messages.
TEMPBASE A base name to use for temporary files; may be NULL to
use a random name.
Returns NULL on error. */
extern struct pex_obj *pex_init (int flags, const char *pname,
const char *tempbase);
/* Flags for pex_run. These are bits to be or'ed together. */
/* Last program in pipeline. Standard output of program goes to
OUTNAME, or, if OUTNAME is NULL, to standard output of caller. Do
not set this if you want to call pex_read_output. After this is
set, pex_run may no longer be called with the same struct
pex_obj. */
#define PEX_LAST 0x1
/* Search for program in executable search path. */
#define PEX_SEARCH 0x2
/* OUTNAME is a suffix. */
#define PEX_SUFFIX 0x4
/* Send program's standard error to standard output. */
#define PEX_STDERR_TO_STDOUT 0x8
/* Input file should be opened in binary mode. This flag is ignored
on Unix. */
#define PEX_BINARY_INPUT 0x10
/* Output file should be opened in binary mode. This flag is ignored
on Unix. For proper behaviour PEX_BINARY_INPUT and
PEX_BINARY_OUTPUT have to match appropriately--i.e., a call using
PEX_BINARY_OUTPUT should be followed by a call using
PEX_BINARY_INPUT. */
#define PEX_BINARY_OUTPUT 0x20
/* Capture stderr to a pipe. The output can be read by
calling pex_read_err and reading from the returned
FILE object. This flag may be specified only for
the last program in a pipeline.
This flag is supported only on Unix and Windows. */
#define PEX_STDERR_TO_PIPE 0x40
/* Capture stderr in binary mode. This flag is ignored
on Unix. */
#define PEX_BINARY_ERROR 0x80
/* Execute one program. Returns NULL on success. On error returns an
error string (typically just the name of a system call); the error
string is statically allocated.
OBJ Returned by pex_init.
FLAGS As above.
EXECUTABLE The program to execute.
ARGV NULL terminated array of arguments to pass to the program.
OUTNAME Sets the output file name as follows:
PEX_SUFFIX set (OUTNAME may not be NULL):
TEMPBASE parameter to pex_init not NULL:
Output file name is the concatenation of TEMPBASE
and OUTNAME.
TEMPBASE is NULL:
Output file name is a random file name ending in
OUTNAME.
PEX_SUFFIX not set:
OUTNAME not NULL:
Output file name is OUTNAME.
OUTNAME NULL, TEMPBASE not NULL:
Output file name is randomly chosen using
TEMPBASE.
OUTNAME NULL, TEMPBASE NULL:
Output file name is randomly chosen.
If PEX_LAST is not set, the output file name is the
name to use for a temporary file holding stdout, if
any (there will not be a file if PEX_USE_PIPES is set
and the system supports pipes). If a file is used, it
will be removed when no longer needed unless
PEX_SAVE_TEMPS is set.
If PEX_LAST is set, and OUTNAME is not NULL, standard
output is written to the output file name. The file
will not be removed. If PEX_LAST and PEX_SUFFIX are
both set, TEMPBASE may not be NULL.
ERRNAME If not NULL, this is the name of a file to which
standard error is written. If NULL, standard error of
the program is standard error of the caller.
ERR On an error return, *ERR is set to an errno value, or
to 0 if there is no relevant errno.
*/
extern const char *pex_run (struct pex_obj *obj, int flags,
const char *executable, char * const *argv,
const char *outname, const char *errname,
int *err);
/* As for pex_run (), but takes an extra parameter to enable the
environment for the child process to be specified.
ENV The environment for the child process, specified as
an array of character pointers. Each element of the
array should point to a string of the form VAR=VALUE,
with the exception of the last element which must be
a null pointer.
*/
extern const char *pex_run_in_environment (struct pex_obj *obj, int flags,
const char *executable,
char * const *argv,
char * const *env,
const char *outname,
const char *errname, int *err);
/* Return a stream for a temporary file to pass to the first program
in the pipeline as input. The file name is chosen as for pex_run.
pex_run closes the file automatically; don't close it yourself. */
extern FILE *pex_input_file (struct pex_obj *obj, int flags,
const char *in_name);
/* Return a stream for a pipe connected to the standard input of the
first program in the pipeline. You must have passed
`PEX_USE_PIPES' to `pex_init'. Close the returned stream
yourself. */
extern FILE *pex_input_pipe (struct pex_obj *obj, int binary);
/* Read the standard output of the last program to be executed.
pex_run can not be called after this. BINARY should be non-zero if
the file should be opened in binary mode; this is ignored on Unix.
Returns NULL on error. Don't call fclose on the returned FILE; it
will be closed by pex_free. */
extern FILE *pex_read_output (struct pex_obj *, int binary);
/* Read the standard error of the last program to be executed.
pex_run can not be called after this. BINARY should be non-zero if
the file should be opened in binary mode; this is ignored on Unix.
Returns NULL on error. Don't call fclose on the returned FILE; it
will be closed by pex_free. */
extern FILE *pex_read_err (struct pex_obj *, int binary);
/* Return exit status of all programs in VECTOR. COUNT indicates the
size of VECTOR. The status codes in the vector are in the order of
the calls to pex_run. Returns 0 on error, 1 on success. */
extern int pex_get_status (struct pex_obj *, int count, int *vector);
/* Return times of all programs in VECTOR. COUNT indicates the size
of VECTOR. struct pex_time is really just struct timeval, but that
is not portable to all systems. Returns 0 on error, 1 on
success. */
struct pex_time
{
unsigned long user_seconds;
unsigned long user_microseconds;
unsigned long system_seconds;
unsigned long system_microseconds;
};
extern int pex_get_times (struct pex_obj *, int count,
struct pex_time *vector);
/* Clean up a pex_obj. If you have not called pex_get_times or
pex_get_status, this will try to kill the subprocesses. */
extern void pex_free (struct pex_obj *);
/* Just execute one program. Return value is as for pex_run.
FLAGS Combination of PEX_SEARCH and PEX_STDERR_TO_STDOUT.
EXECUTABLE As for pex_run.
ARGV As for pex_run.
PNAME As for pex_init.
OUTNAME As for pex_run when PEX_LAST is set.
ERRNAME As for pex_run.
STATUS Set to exit status on success.
ERR As for pex_run.
*/
extern const char *pex_one (int flags, const char *executable,
char * const *argv, const char *pname,
const char *outname, const char *errname,
int *status, int *err);
/* pexecute and pwait are the old pexecute interface, still here for
backward compatibility. Don't use these for new code. Instead,
use pex_init/pex_run/pex_get_status/pex_free, or pex_one. */
/* Definitions used by the pexecute routine. */
#define PEXECUTE_FIRST 1
#define PEXECUTE_LAST 2
#define PEXECUTE_ONE (PEXECUTE_FIRST + PEXECUTE_LAST)
#define PEXECUTE_SEARCH 4
#define PEXECUTE_VERBOSE 8
/* Execute a program. */
extern int pexecute (const char *, char * const *, const char *,
const char *, char **, char **, int);
/* Wait for pexecute to finish. */
extern int pwait (int, int *, int);
#if !HAVE_DECL_ASPRINTF
/* Like sprintf but provides a pointer to malloc'd storage, which must
be freed by the caller. */
extern int asprintf (char **, const char *, ...) ATTRIBUTE_PRINTF_2;
#endif
#if !HAVE_DECL_VASPRINTF
/* Like vsprintf but provides a pointer to malloc'd storage, which
must be freed by the caller. */
extern int vasprintf (char **, const char *, va_list) ATTRIBUTE_PRINTF(2,0);
#endif
#if defined(HAVE_DECL_SNPRINTF) && !HAVE_DECL_SNPRINTF
/* Like sprintf but prints at most N characters. */
extern int snprintf (char *, size_t, const char *, ...) ATTRIBUTE_PRINTF_3;
#endif
#if defined(HAVE_DECL_VSNPRINTF) && !HAVE_DECL_VSNPRINTF
/* Like vsprintf but prints at most N characters. */
extern int vsnprintf (char *, size_t, const char *, va_list) ATTRIBUTE_PRINTF(3,0);
#endif
#if defined(HAVE_DECL_STRVERSCMP) && !HAVE_DECL_STRVERSCMP
/* Compare version strings. */
extern int strverscmp (const char *, const char *);
#endif
/* Set the title of a process */
extern void setproctitle (const char *name, ...);
/* Increase stack limit if possible. */
extern void stack_limit_increase (unsigned long);
#define ARRAY_SIZE(a) (sizeof (a) / sizeof ((a)[0]))
/* Drastically simplified alloca configurator. If we're using GCC,
we use __builtin_alloca; otherwise we use the C alloca. The C
alloca is always available. You can override GCC by defining
USE_C_ALLOCA yourself. The canonical autoconf macro C_ALLOCA is
also set/unset as it is often used to indicate whether code needs
to call alloca(0). */
extern void *C_alloca (size_t) ATTRIBUTE_MALLOC;
#undef alloca
#if GCC_VERSION >= 2000 && !defined USE_C_ALLOCA
# define alloca(x) __builtin_alloca(x)
# undef C_ALLOCA
# define ASTRDUP(X) \
(__extension__ ({ const char *const libiberty_optr = (X); \
const unsigned long libiberty_len = strlen (libiberty_optr) + 1; \
char *const libiberty_nptr = (char *const) alloca (libiberty_len); \
(char *) memcpy (libiberty_nptr, libiberty_optr, libiberty_len); }))
#else
# define alloca(x) C_alloca(x)
# undef USE_C_ALLOCA
# define USE_C_ALLOCA 1
# undef C_ALLOCA
# define C_ALLOCA 1
extern const char *libiberty_optr;
extern char *libiberty_nptr;
extern unsigned long libiberty_len;
# define ASTRDUP(X) \
(libiberty_optr = (X), \
libiberty_len = strlen (libiberty_optr) + 1, \
libiberty_nptr = (char *) alloca (libiberty_len), \
(char *) memcpy (libiberty_nptr, libiberty_optr, libiberty_len))
#endif
#ifdef __cplusplus
}
#endif
#endif /* ! defined (LIBIBERTY_H) */

View file

@ -0,0 +1,154 @@
/* ###
* IP: LGPL 3.0
* REVIEWED: YES
*/
/* <ctype.h> replacement macros.
Copyright (C) 2000, 2001 Free Software Foundation, Inc.
Contributed by Zack Weinberg <zackw@stanford.edu>.
This file is part of the libiberty library.
Libiberty is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
Libiberty 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
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with libiberty; see the file COPYING.LIB. If
not, write to the Free Software Foundation, Inc., 51 Franklin Street - Fifth Floor,
Boston, MA 02110-1301, USA. */
/* This is a compatible replacement of the standard C library's <ctype.h>
with the following properties:
- Implements all isxxx() macros required by C99.
- Also implements some character classes useful when
parsing C-like languages.
- Does not change behavior depending on the current locale.
- Behaves properly for all values in the range of a signed or
unsigned char.
To avoid conflicts, this header defines the isxxx functions in upper
case, e.g. ISALPHA not isalpha. */
#ifndef SAFE_CTYPE_H
#define SAFE_CTYPE_H
/* Determine host character set. */
#define HOST_CHARSET_UNKNOWN 0
#define HOST_CHARSET_ASCII 1
#define HOST_CHARSET_EBCDIC 2
#if '\n' == 0x0A && ' ' == 0x20 && '0' == 0x30 \
&& 'A' == 0x41 && 'a' == 0x61 && '!' == 0x21
# define HOST_CHARSET HOST_CHARSET_ASCII
#else
# if '\n' == 0x15 && ' ' == 0x40 && '0' == 0xF0 \
&& 'A' == 0xC1 && 'a' == 0x81 && '!' == 0x5A
# define HOST_CHARSET HOST_CHARSET_EBCDIC
# else
# define HOST_CHARSET HOST_CHARSET_UNKNOWN
# endif
#endif
/* Categories. */
enum {
/* In C99 */
_sch_isblank = 0x0001, /* space \t */
_sch_iscntrl = 0x0002, /* nonprinting characters */
_sch_isdigit = 0x0004, /* 0-9 */
_sch_islower = 0x0008, /* a-z */
_sch_isprint = 0x0010, /* any printing character including ' ' */
_sch_ispunct = 0x0020, /* all punctuation */
_sch_isspace = 0x0040, /* space \t \n \r \f \v */
_sch_isupper = 0x0080, /* A-Z */
_sch_isxdigit = 0x0100, /* 0-9A-Fa-f */
/* Extra categories useful to cpplib. */
_sch_isidst = 0x0200, /* A-Za-z_ */
_sch_isvsp = 0x0400, /* \n \r */
_sch_isnvsp = 0x0800, /* space \t \f \v \0 */
/* Combinations of the above. */
_sch_isalpha = _sch_isupper|_sch_islower, /* A-Za-z */
_sch_isalnum = _sch_isalpha|_sch_isdigit, /* A-Za-z0-9 */
_sch_isidnum = _sch_isidst|_sch_isdigit, /* A-Za-z0-9_ */
_sch_isgraph = _sch_isalnum|_sch_ispunct, /* isprint and not space */
_sch_iscppsp = _sch_isvsp|_sch_isnvsp, /* isspace + \0 */
_sch_isbasic = _sch_isprint|_sch_iscppsp /* basic charset of ISO C
(plus ` and @) */
};
/* Character classification. */
extern const unsigned short _sch_istable[256];
#define _sch_test(c, bit) (_sch_istable[(c) & 0xff] & (unsigned short)(bit))
#define ISALPHA(c) _sch_test(c, _sch_isalpha)
#define ISALNUM(c) _sch_test(c, _sch_isalnum)
#define ISBLANK(c) _sch_test(c, _sch_isblank)
#define ISCNTRL(c) _sch_test(c, _sch_iscntrl)
#define ISDIGIT(c) _sch_test(c, _sch_isdigit)
#define ISGRAPH(c) _sch_test(c, _sch_isgraph)
#define ISLOWER(c) _sch_test(c, _sch_islower)
#define ISPRINT(c) _sch_test(c, _sch_isprint)
#define ISPUNCT(c) _sch_test(c, _sch_ispunct)
#define ISSPACE(c) _sch_test(c, _sch_isspace)
#define ISUPPER(c) _sch_test(c, _sch_isupper)
#define ISXDIGIT(c) _sch_test(c, _sch_isxdigit)
#define ISIDNUM(c) _sch_test(c, _sch_isidnum)
#define ISIDST(c) _sch_test(c, _sch_isidst)
#define IS_ISOBASIC(c) _sch_test(c, _sch_isbasic)
#define IS_VSPACE(c) _sch_test(c, _sch_isvsp)
#define IS_NVSPACE(c) _sch_test(c, _sch_isnvsp)
#define IS_SPACE_OR_NUL(c) _sch_test(c, _sch_iscppsp)
/* Character transformation. */
extern const unsigned char _sch_toupper[256];
extern const unsigned char _sch_tolower[256];
#define TOUPPER(c) _sch_toupper[(c) & 0xff]
#define TOLOWER(c) _sch_tolower[(c) & 0xff]
/* Prevent the users of safe-ctype.h from accidently using the routines
from ctype.h. Initially, the approach was to produce an error when
detecting that ctype.h has been included. But this was causing
trouble as ctype.h might get indirectly included as a result of
including another system header (for instance gnulib's stdint.h).
So we include ctype.h here and then immediately redefine its macros. */
#include <ctype.h>
#undef isalpha
#define isalpha(c) do_not_use_isalpha_with_safe_ctype
#undef isalnum
#define isalnum(c) do_not_use_isalnum_with_safe_ctype
#undef iscntrl
#define iscntrl(c) do_not_use_iscntrl_with_safe_ctype
#undef isdigit
#define isdigit(c) do_not_use_isdigit_with_safe_ctype
#undef isgraph
#define isgraph(c) do_not_use_isgraph_with_safe_ctype
#undef islower
#define islower(c) do_not_use_islower_with_safe_ctype
#undef isprint
#define isprint(c) do_not_use_isprint_with_safe_ctype
#undef ispunct
#define ispunct(c) do_not_use_ispunct_with_safe_ctype
#undef isspace
#define isspace(c) do_not_use_isspace_with_safe_ctype
#undef isupper
#define isupper(c) do_not_use_isupper_with_safe_ctype
#undef isxdigit
#define isxdigit(c) do_not_use_isxdigit_with_safe_ctype
#undef toupper
#define toupper(c) do_not_use_toupper_with_safe_ctype
#undef tolower
#define tolower(c) do_not_use_tolower_with_safe_ctype
#endif /* SAFE_CTYPE_H */