#if defined(__FreeBSD__) || defined(__NetBSD__)
# include <sys/param.h>
# include <sys/types.h>
# include <sys/sysctl.h>
#endif
#include <stdlib.h>
#include <stdio.h>
#include "Xosdefs.h"
#include <string.h>
#include <ctype.h>
#ifdef WIN32
# include "Xw32defs.h"
#endif
#if 0
#ifndef X_NOT_POSIX
# ifndef _POSIX_SOURCE
# define _POSIX_SOURCE
# endif
#endif
#endif
#include <sys/types.h>
#include <fcntl.h>
#ifdef X_NOT_POSIX
# ifndef WIN32
# include <sys/file.h>
# endif
#else
# include <unistd.h>
#endif
#ifdef ISC
# include <unistd.h>
#endif
#if defined(X_NOT_POSIX) || defined(_POSIX_SOURCE)
# include <signal.h>
#else
# define _POSIX_SOURCE
# include <signal.h>
# undef _POSIX_SOURCE
#endif
#if !defined(SIGCHLD) && defined(SIGCLD)
# define SIGCHLD SIGCLD
#endif
#include <sys/stat.h>
#ifndef X_NOT_POSIX
# ifdef _POSIX_SOURCE
# ifdef SCO325
# include <sys/procset.h>
# include <sys/siginfo.h>
# endif
# include <sys/wait.h>
# else
# define _POSIX_SOURCE
# include <sys/wait.h>
# undef _POSIX_SOURCE
# endif
# define waitCode(w) WEXITSTATUS(w)
# define waitSig(w) WTERMSIG(w)
typedef int waitType;
#else
# ifdef SYSV
# define waitCode(w) (((w) >> 8) & 0x7f)
# define waitSig(w) ((w) & 0xff)
typedef int waitType;
# else
# ifdef WIN32
# include <process.h>
typedef int waitType;
# else
# include <sys/wait.h>
# define waitCode(w) ((w).w_T.w_Retcode)
# define waitSig(w) ((w).w_T.w_Termsig)
typedef union wait waitType;
# endif
# endif
# ifndef WIFSIGNALED
# define WIFSIGNALED(w) waitSig(w)
# endif
# ifndef WIFEXITED
# define WIFEXITED(w) waitCode(w)
# endif
#endif
# include <stdlib.h>
#if defined(macII) && !defined(__STDC__)
char *malloc(), *realloc();
#endif
#include <errno.h>
#ifdef __minix_vmd
#define USE_FREOPEN 1
#endif
#if !((defined(sun) && !defined(SVR4)) || defined(macII))
#define USE_STRERROR 1
#endif
#ifndef WIN32
#include <sys/utsname.h>
#else
#include <windows.h>
#endif
#ifndef SYS_NMLN
# ifdef _SYS_NMLN
# define SYS_NMLN _SYS_NMLN
# else
# define SYS_NMLN 257
# endif
#endif
#if defined(linux) || defined(__GNU__)
#include <limits.h>
#include <stdio.h>
#endif
#ifdef __QNX__
#include <unix.h>
#endif
#ifndef USE_STRERROR
# ifndef strerror
extern char *sys_errlist[];
extern int sys_nerr;
# define strerror(n) \
(((n) >= 0 && (n) < sys_nerr) ? sys_errlist[n] : "unknown error")
# endif
#endif
#if defined(__NetBSD__)
#include <sys/utsname.h>
#endif
#if !(defined(Lynx) || defined(__Lynx__) || (defined(SVR4) && !defined(sun))) && !defined (__CYGWIN__)
#define HAS_MKSTEMP
#endif
typedef unsigned char boolean;
#define TRUE 1
#define FALSE 0
# include "imakemdep.h"
#ifdef CROSSCOMPILE
# include "imakemdep_cpp.h"
#endif
#if defined CROSSCOMPILE || defined FIXUP_CPP_WHITESPACE
int InRule = FALSE;
#endif
#if defined CROSSCOMPILE || defined INLINE_SYNTAX
int InInline = 0;
#endif
#if defined CROSSCOMPILE || defined MAGIC_MAKE_VARS
int xvariable = 0;
int xvariables[10];
#endif
#ifndef PATH_MAX
#define PATH_MAX 1024
#endif
void KludgeOutputLine(char **), KludgeResetRule(void);
#ifndef CROSSCOMPILE
# ifdef USE_CC_E
# ifndef DEFAULT_CC
# define DEFAULT_CC "cc"
# endif
# else
# ifndef DEFAULT_CPP
# ifdef CPP_PROGRAM
# define DEFAULT_CPP CPP_PROGRAM
# else
# define DEFAULT_CPP "/lib/cpp"
# endif
# endif
# endif
#endif
char *cpp = NULL;
char *tmpMakefile = "/tmp/Imf.XXXXXX";
char *tmpImakefile = "/tmp/IIf.XXXXXX";
char *make_argv[ ARGUMENTS ] = {
#ifdef WIN32
"nmake"
#else
"make"
#endif
};
int make_argindex;
int cpp_argindex;
char *Imakefile = NULL;
char *Makefile = "Makefile";
char *Template = "Imake.tmpl";
char *ImakefileC = "Imakefile.c";
boolean haveImakefileC = FALSE;
char *cleanedImakefile = NULL;
char *program;
char *FindImakefile(char *Imakefile);
char *ReadLine(FILE *tmpfd, char *tmpfname);
char *CleanCppInput(char *imakefile);
char *Strdup(char *cp);
char *Emalloc(int size);
void LogFatalI(char *s, int i), LogFatal(char *x0, char *x1),
LogMsg(char *x0, char *x1);
void showit(FILE *fd);
void wrapup(void);
void init(void);
void AddMakeArg(char *arg);
void AddCppArg(char *arg);
#ifdef CROSSCOMPILE
char *CrossCompileCPP(void);
#endif
void SetOpts(int argc, char **argv);
void CheckImakefileC(char *masterc);
void cppit(char *imakefile, char *template, char *masterc,
FILE *outfd, char *outfname);
void makeit(void);
void CleanCppOutput(FILE *tmpfd, char *tmpfname);
boolean isempty(char *line);
void writetmpfile(FILE *fd, char *buf, int cnt, char *fname);
#ifdef SIGNALRETURNSINT
int catch(int sig);
#else
void catch(int sig);
#endif
void showargs(char **argv);
boolean optional_include(FILE *inFile, char *defsym, char *fname);
void doit(FILE *outfd, char *cmd, char **argv);
boolean define_os_defaults(FILE *inFile);
#ifdef CROSSCOMPILE
static void get_cross_compile_dir(FILE *inFile);
#endif
#ifdef CROSSCOMPILEDIR
char *CrossCompileDir = CROSSCOMPILEDIR;
#else
char *CrossCompileDir = "";
#endif
boolean CrossCompiling = FALSE;
boolean verbose = FALSE;
boolean show = TRUE;
int
main(int argc, char *argv[])
{
FILE *tmpfd = NULL;
char makeMacro[ BUFSIZ ];
char makefileMacro[ BUFSIZ ];
int lenCrossCompileDir = 0;
program = argv[0];
init();
lenCrossCompileDir = strlen(CrossCompileDir);
if (lenCrossCompileDir) {
if (lenCrossCompileDir > (PATH_MAX - 20))
LogFatal("Cross compile directory path too long %s\n",
CrossCompileDir);
else
CrossCompiling = TRUE;
}
SetOpts(argc, argv);
Imakefile = FindImakefile(Imakefile);
CheckImakefileC(ImakefileC);
if (Makefile) {
tmpMakefile = Makefile;
if ((tmpfd = fopen(tmpMakefile, "w+")) == NULL)
LogFatal("Cannot create temporary file %s.", tmpMakefile);
} else {
#ifdef HAS_MKSTEMP
int fd;
#endif
tmpMakefile = Strdup(tmpMakefile);
#ifndef HAS_MKSTEMP
if (mktemp(tmpMakefile) == NULL ||
(tmpfd = fopen(tmpMakefile, "w+")) == NULL) {
LogFatal("Cannot create temporary file %s.", tmpMakefile);
}
#else
fd = mkstemp(tmpMakefile);
if (fd == -1 || (tmpfd = fdopen(fd, "w+")) == NULL) {
if (fd != -1) {
unlink(tmpMakefile); close(fd);
}
LogFatal("Cannot create temporary file %s.", tmpMakefile);
}
#endif
}
AddMakeArg("-f");
AddMakeArg( tmpMakefile );
sprintf(makeMacro, "MAKE=%s", program);
AddMakeArg( makeMacro );
sprintf(makefileMacro, "MAKEFILE=%s", Imakefile);
AddMakeArg( makefileMacro );
cleanedImakefile = CleanCppInput(Imakefile);
cppit(cleanedImakefile, Template, ImakefileC, tmpfd, tmpMakefile);
if (show) {
if (Makefile == NULL)
showit(tmpfd);
} else
makeit();
wrapup();
exit(0);
}
void
showit(FILE *fd)
{
char buf[ BUFSIZ ];
int red;
fseek(fd, 0, 0);
while ((red = fread(buf, 1, BUFSIZ, fd)) > 0)
writetmpfile(stdout, buf, red, "stdout");
if (red < 0)
LogFatal("Cannot read %s.", tmpMakefile);
}
void
wrapup(void)
{
if (tmpMakefile != Makefile)
unlink(tmpMakefile);
if (cleanedImakefile && cleanedImakefile != Imakefile)
unlink(cleanedImakefile);
if (haveImakefileC)
unlink(ImakefileC);
}
#ifdef SIGNALRETURNSINT
int
#else
void
#endif
catch(int sig)
{
errno = 0;
LogFatalI("Signal %d.", sig);
}
void
init(void)
{
register char *p;
make_argindex=0;
while (make_argv[ make_argindex ] != NULL)
make_argindex++;
cpp_argindex = 0;
while (cpp_argv[ cpp_argindex ] != NULL)
cpp_argindex++;
#if defined CROSSCOMPILE
if (sys == netBSD)
if (CrossCompiling) {
LogFatal("fix imake to do crosscompiling for NetBSD\n","");
} else
#endif
#if defined(__NetBSD__) || defined CROSSCOMPILE
{
struct utsname uts;
static char argument[512];
if (uname(&uts) != 0)
LogFatal("uname(3) failed; can't tell what %s",
"kind of machine you have.");
memset(argument, 0, sizeof(argument));
(void)snprintf(argument, sizeof(argument) - 1,
"-D__%s__", uts.machine);
AddCppArg(argument);
}
#endif
if ((p = getenv("IMAKEINCLUDE"))) {
if (*p != '-' || *(p+1) != 'I')
LogFatal("Environment var IMAKEINCLUDE %s",
"must begin with -I");
AddCppArg(p);
for (; *p; p++)
if (*p == ' ') {
*p++ = '\0';
AddCppArg(p);
}
}
if ((p = getenv("IMAKECPP")))
cpp = p;
if ((p = getenv("IMAKEMAKE")))
make_argv[0] = p;
if (signal(SIGINT, SIG_IGN) != SIG_IGN)
signal(SIGINT, catch);
#ifdef SIGCHLD
signal(SIGCHLD, SIG_DFL);
#endif
}
void
AddMakeArg(char *arg)
{
errno = 0;
if (make_argindex >= ARGUMENTS-1)
LogFatal("Out of internal storage.", "");
make_argv[ make_argindex++ ] = arg;
make_argv[ make_argindex ] = NULL;
}
void
AddCppArg(char *arg)
{
errno = 0;
if (cpp_argindex >= ARGUMENTS-1)
LogFatal("Out of internal storage.", "");
cpp_argv[ cpp_argindex++ ] = arg;
cpp_argv[ cpp_argindex ] = NULL;
}
void
SetOpts(int argc, char **argv)
{
errno = 0;
for(argc--, argv++; argc; argc--, argv++) {
if (argv[0][0] == '-') {
if (argv[0][1] == 'D') {
AddCppArg(argv[0]);
} else if (argv[0][1] == 'I') {
AddCppArg(argv[0]);
} else if (argv[0][1] == 'U') {
AddCppArg(argv[0]);
} else if (argv[0][1] == 'W') {
AddCppArg(argv[0]);
} else if (argv[0][1] == 'f') {
if (argv[0][2])
Imakefile = argv[0]+2;
else {
argc--, argv++;
if (! argc)
LogFatal("No description arg after -f flag", "");
Imakefile = argv[0];
}
} else if (argv[0][1] == 's') {
if (argv[0][2])
Makefile = ((argv[0][2] == '-') && !argv[0][3]) ?
NULL : argv[0]+2;
else {
argc--, argv++;
if (!argc)
LogFatal("No description arg after -s flag", "");
Makefile = ((argv[0][0] == '-') && !argv[0][1]) ?
NULL : argv[0];
}
show = TRUE;
} else if (argv[0][1] == 'e') {
Makefile = (argv[0][2] ? argv[0]+2 : NULL);
show = FALSE;
} else if (argv[0][1] == 'T') {
if (argv[0][2])
Template = argv[0]+2;
else {
argc--, argv++;
if (! argc)
LogFatal("No description arg after -T flag", "");
Template = argv[0];
}
} else if (argv[0][1] == 'C') {
if (argv[0][2])
ImakefileC = argv[0]+2;
else {
argc--, argv++;
if (! argc)
LogFatal("No imakeCfile arg after -C flag", "");
ImakefileC = argv[0];
}
} else if (argv[0][1] == 'v') {
verbose = TRUE;
} else
AddMakeArg(argv[0]);
} else
AddMakeArg(argv[0]);
}
#ifndef CROSSCOMPILE
# ifdef USE_CC_E
if (!cpp)
{
AddCppArg("-E");
#ifdef __GNUC__
if (verbose)
AddCppArg("-v");
#endif
cpp = DEFAULT_CC;
}
# else
if (!cpp)
cpp = DEFAULT_CPP;
# endif
#else
if (!cpp)
cpp = CrossCompileCPP();
#endif
cpp_argv[0] = cpp;
AddCppArg(ImakefileC);
}
char *
FindImakefile(char *Imakefile)
{
if (Imakefile) {
if (access(Imakefile, R_OK) < 0)
LogFatal("Cannot find %s.", Imakefile);
} else {
if (access("Imakefile", R_OK) < 0) {
if (access("imakefile", R_OK) < 0)
LogFatal("No description file.", "");
else
Imakefile = "imakefile";
} else
Imakefile = "Imakefile";
}
return(Imakefile);
}
void
LogFatalI(char *s, int i)
{
LogFatal(s, (char *)(long)i);
}
void
LogFatal(char *x0, char *x1)
{
static boolean entered = FALSE;
if (entered)
return;
entered = TRUE;
LogMsg(x0, x1);
fprintf(stderr, " Stop.\n");
wrapup();
exit(1);
}
void
LogMsg(char *x0, char *x1)
{
int error_number = errno;
if (error_number) {
fprintf(stderr, "%s: ", program);
fprintf(stderr, "%s\n", strerror(error_number));
}
fprintf(stderr, "%s: ", program);
fprintf(stderr, x0, x1);
fprintf(stderr, "\n");
}
void
showargs(char **argv)
{
for (; *argv; argv++)
fprintf(stderr, "%s ", *argv);
fprintf(stderr, "\n");
}
#define ImakefileCHeader "/* imake - temporary file */"
void
CheckImakefileC(char *masterc)
{
char mkcbuf[1024];
FILE *inFile;
if (access(masterc, F_OK) == 0) {
inFile = fopen(masterc, "r");
if (inFile == NULL)
LogFatal("Refuse to overwrite: %s", masterc);
if ((fgets(mkcbuf, sizeof(mkcbuf), inFile) &&
strncmp(mkcbuf, ImakefileCHeader,
sizeof(ImakefileCHeader)-1)))
{
fclose(inFile);
LogFatal("Refuse to overwrite: %s", masterc);
}
fclose(inFile);
}
}
#define LocalDefineFmt "#define %s \"%s\"\n"
#define IncludeFmt "#include %s\n"
#define ImakeDefSym "INCLUDE_IMAKEFILE"
#define ImakeTmplSym "IMAKE_TEMPLATE"
#define OverrideWarning "Warning: local file \"%s\" overrides global macros."
boolean
optional_include(FILE *inFile, char *defsym, char *fname)
{
errno = 0;
if (access(fname, R_OK) == 0) {
LogMsg(OverrideWarning, fname);
return (fprintf(inFile, LocalDefineFmt, defsym, fname) < 0 ||
fprintf(inFile, IncludeFmt, defsym) < 0);
}
return FALSE;
}
void
doit(FILE *outfd, char *cmd, char **argv)
{
int pid;
waitType status;
#ifdef WIN32
if (outfd)
dup2(fileno(outfd), 1);
status = _spawnvp(_P_WAIT, cmd, argv);
if (status < 0)
LogFatal("Cannot spawn %s.", cmd);
if (status > 0)
LogFatalI("Exit code %d.", status);
#else
pid = fork();
if (pid < 0)
LogFatal("Cannot fork.", "");
if (pid) {
while (wait(&status) > 0) {
errno = 0;
if (WIFSIGNALED(status))
LogFatalI("Signal %d.", waitSig(status));
if (WIFEXITED(status) && waitCode(status))
LogFatalI("Exit code %d.", waitCode(status));
}
}
else {
if (verbose)
showargs(argv);
if (outfd)
dup2(fileno(outfd), 1);
execvp(cmd, argv);
LogFatal("Cannot exec %s.", cmd);
}
#endif
}
#if !defined WIN32
static void
parse_utsname(struct utsname *name, char *fmt, char *result, char *msg)
{
char buf[SYS_NMLN * 5 + 1];
char *ptr = buf;
int arg;
if (!name)
LogFatal(msg,fmt);
for (arg = 0; fmt[arg] != ' '; arg++)
{
if (arg >= 5)
LogFatal(msg, fmt);
switch (fmt[arg])
{
case 's':
if (arg > 0)
*ptr++ = ' ';
strcpy(ptr, name->sysname);
ptr += strlen(ptr);
break;
case 'n':
if (arg > 0)
*ptr++ = ' ';
strcpy(ptr, name->nodename);
ptr += strlen(ptr);
break;
case 'r':
if (arg > 0)
*ptr++ = ' ';
strcpy(ptr, name->release);
ptr += strlen(ptr);
break;
case 'v':
if (arg > 0)
*ptr++ = ' ';
strcpy(ptr, name->version);
ptr += strlen(ptr);
break;
case 'm':
if (arg > 0)
*ptr++ = ' ';
strcpy(ptr, name->machine);
ptr += strlen(ptr);
break;
default:
LogFatal(msg, fmt);
}
}
if (strlen(buf) >= sizeof(buf))
LogFatal("Buffer overflow parsing uname.", "");
*result = '\0';
(void) sscanf(buf, fmt + arg + 1, result);
}
static char *
trim_version(char *p)
{
if (p != 0 && *p != '\0')
{
while ((*p == '0' || *p == '.') && *(p + 1) != '\0')
++p;
}
return (p);
}
#endif
#if defined linux
const char *libc_c=
"#include <stdio.h>\n"
"#include <ctype.h>\n"
"\n"
"#if 1\n"
"#pragma weak gnu_get_libc_version\n"
"#pragma weak __libc_version\n"
"#pragma weak __linux_C_lib_version\n"
"#endif\n"
"\n"
"extern const char * gnu_get_libc_version (void);\n"
"extern const char * __linux_C_lib_version;\n"
"extern const char __libc_version [];\n"
"\n"
"int\n"
"main ()\n"
"{\n"
" int libcmajor = 0, libcminor = 0, libcteeny = 0;\n"
" const char * ptr = NULL;\n"
" int glibcmajor = 0;\n"
"\n"
" if (gnu_get_libc_version != 0)\n"
" {\n"
" ptr = gnu_get_libc_version ();\n"
" glibcmajor = 4;\n"
" }\n"
" else if (&__libc_version != 0)\n"
" {\n"
" ptr = __libc_version;\n"
" glibcmajor = 4;\n"
" }\n"
" else if (&__linux_C_lib_version != 0)\n"
" {\n"
" ptr = __linux_C_lib_version;\n"
" }\n"
" else\n"
" {\n"
" libcmajor = 0; libcminor = 0; libcteeny = 0;\n"
" }\n"
"\n"
" if (ptr)\n"
" {\n"
" while (!isdigit (*ptr))\n"
" ptr++;\n"
"\n"
" sscanf (ptr, \"%d.%d.%d\", &libcmajor, &libcminor, &libcteeny);\n"
" libcmajor += glibcmajor;\n"
" }\n"
"\n"
" printf(\"#define DefaultLinuxCLibMajorVersion %d\\n\", libcmajor);\n"
" printf(\"#define DefaultLinuxCLibMinorVersion %d\\n\", libcminor);\n"
" printf(\"#define DefaultLinuxCLibTeenyVersion %d\\n\", libcteeny);\n"
"\n"
" return 0;\n"
"}\n"
;
static void
get_libc_version(FILE *inFile)
{
char aout[] = "/tmp/imakeXXXXXX";
FILE *fp;
const char *format = "%s -o %s -x c -";
char *cc;
int len;
char *command;
{
int tmpfd;
if ((tmpfd = mkstemp(aout)) == -1) {
perror("mkstemp");
abort();
}
close(tmpfd);
}
cc = getenv ("CC");
if (cc == NULL)
cc = "gcc";
len = strlen (aout) + strlen (format) + strlen (cc);
if (len < 128) len = 128;
command = alloca (len);
if (snprintf (command , len, format, cc, aout) == len)
abort ();
fp = popen (command, "w");
if (fp == NULL || fprintf (fp, "%s\n", libc_c) < 0
|| pclose (fp) != 0)
abort ();
fp = popen (aout, "r");
if (fp == NULL)
abort ();
while (fgets (command, len, fp))
fprintf (inFile, command);
len = pclose (fp);
remove (aout);
if (len)
abort ();
}
#endif
#if defined(__OpenBSD__)
static void
get_stackprotector(FILE *inFile)
{
FILE *fp;
char *cc;
char command[1024], buf[1024];
cc = getenv("CC");
if (cc == NULL) {
cc = "cc";
}
snprintf(command, sizeof(command), "%s -v 2>&1", cc);
fp = popen(command, "r");
if (fp == NULL)
abort();
while (fgets(buf, sizeof(buf), fp)) {
if (strstr(buf, "propolice") != NULL) {
fprintf(inFile, "#define HasGccStackProtector YES\n");
break;
}
}
if (pclose(fp))
abort();
}
#endif
#if defined CROSSCOMPILE || defined linux
static void
get_distrib(FILE *inFile)
{
struct stat sb;
static char* suse = "/etc/SuSE-release";
static char* redhat = "/etc/redhat-release";
static char* debian = "/etc/debian_version";
fprintf (inFile, "%s\n", "#define LinuxUnknown 0");
fprintf (inFile, "%s\n", "#define LinuxSuSE 1");
fprintf (inFile, "%s\n", "#define LinuxCaldera 2");
fprintf (inFile, "%s\n", "#define LinuxCraftworks 3");
fprintf (inFile, "%s\n", "#define LinuxDebian 4");
fprintf (inFile, "%s\n", "#define LinuxInfoMagic 5");
fprintf (inFile, "%s\n", "#define LinuxKheops 6");
fprintf (inFile, "%s\n", "#define LinuxPro 7");
fprintf (inFile, "%s\n", "#define LinuxRedHat 8");
fprintf (inFile, "%s\n", "#define LinuxSlackware 9");
fprintf (inFile, "%s\n", "#define LinuxTurbo 10");
fprintf (inFile, "%s\n", "#define LinuxWare 11");
fprintf (inFile, "%s\n", "#define LinuxYggdrasil 12");
#ifdef CROSSCOMPILE
if (CrossCompiling) {
fprintf (inFile, "%s\n",
"#define DefaultLinuxDistribution LinuxUnknown");
fprintf (inFile, "%s\n", "#define DefaultLinuxDistName Unknown");
return;
}
#endif
if (lstat (suse, &sb) == 0) {
fprintf (inFile, "%s\n", "#define DefaultLinuxDistribution LinuxSuSE");
fprintf (inFile, "%s\n", "#define DefaultLinuxDistName SuSE");
return;
}
if (lstat (redhat, &sb) == 0) {
fprintf (inFile, "%s\n", "#define DefaultLinuxDistribution LinuxRedHat");
fprintf (inFile, "%s\n", "#define DefaultLinuxDistName RedHat");
return;
}
if (lstat (debian, &sb) == 0) {
fprintf (inFile, "%s\n", "#define DefaultLinuxDistribution LinuxDebian");
fprintf (inFile, "%s\n", "#define DefaultLinuxDistName Debian");
return;
}
fprintf (inFile, "%s\n", "#define DefaultLinuxDistribution LinuxUnknown");
fprintf (inFile, "%s\n", "#define DefaultLinuxDistName Unknown");
}
static void
get_ld_version(FILE *inFile)
{
FILE* ldprog;
signed char c;
int ldmajor, ldminor;
const char *ld = "ld -v";
#ifdef CROSSCOMPILE
if (CrossCompiling) {
char cmd[PATH_MAX];
strcpy (cmd, CrossCompileDir);
strcat (cmd,"/");
strcat (cmd,ld);
ldprog = popen (cmd, "r");
} else
#endif
ldprog = popen (ld, "r");
if (ldprog) {
do {
c = fgetc (ldprog);
} while (c != EOF && !isdigit (c));
ungetc (c, ldprog);
(void) fscanf (ldprog, "%d.%d", &ldmajor, &ldminor);
if ((ldmajor > 2) || ((ldmajor == 2) && (ldminor > 9)))
ldmajor *= 100;
else
ldmajor *= 10;
fprintf(inFile, "#define DefaultLinuxBinUtilsMajorVersion %d\n",
ldmajor + ldminor);
pclose (ldprog);
}
}
#endif
#if defined __FreeBSD__
static void
get_binary_format(FILE *inFile)
{
int mib[2];
size_t len;
int osrel = 0;
FILE *objprog = NULL;
int iself = 0;
char buf[10];
char cmd[PATH_MAX];
mib[0] = CTL_KERN;
mib[1] = KERN_OSRELDATE;
len = sizeof(osrel);
sysctl(mib, 2, &osrel, &len, NULL, 0);
if (CrossCompiling) {
strcpy (cmd, CrossCompileDir);
strcat (cmd, "/");
strcat (cmd,"objformat");
} else
strcpy (cmd, "objformat");
if (osrel >= 300004 &&
(objprog = popen(cmd, "r")) != NULL &&
fgets(buf, sizeof(buf), objprog) != NULL &&
strncmp(buf, "elf", 3) == 0)
iself = 1;
if (objprog)
pclose(objprog);
fprintf(inFile, "#define DefaultToElfFormat %s\n", iself ? "YES" : "NO");
}
#endif
#if defined(sun) && defined(__SVR4)
static void
get_sun_compiler_versions (FILE *inFile)
{
char buf[PATH_MAX];
char cmd[PATH_MAX];
static char* sunpro_cc = "/opt/SUNWspro/bin/cc";
static char* sunpro_CC = "/opt/SUNWspro/bin/CC";
int cmajor, cminor;
char* vptr;
struct stat sb;
FILE* ccproc;
#if defined CROSSCOMPILE
if (CrossCompiling) {
int len = strlen(CrossCompileDir);
len += 3;
sunpro_cc = (char *) malloc(len);
sunpro_CC = (char *) malloc(len);
strcpy(sunpro_cc,CrossCompileDir);
strcpy(sunpro_CC,CrossCompileDir);
strcat(sunpro_cc,"/cc");
strcat(sunpro_CC,"/CC");
}
#endif
if (lstat (sunpro_cc, &sb) == 0) {
strcpy (cmd, sunpro_cc);
strcat (cmd, " -V 2>&1");
if ((ccproc = popen (cmd, "r")) != NULL) {
if (fgets (buf, PATH_MAX, ccproc) != NULL) {
vptr = strrchr (buf, 'C');
for (; !isdigit(*vptr); vptr++);
(void) sscanf (vptr, "%d.%d", &cmajor, &cminor);
fprintf (inFile,
"#define DefaultSunProCCompilerMajorVersion %d\n",
cmajor);
fprintf (inFile,
"#define DefaultSunProCCompilerMinorVersion %d\n",
cminor);
}
while (fgets (buf, PATH_MAX, ccproc) != NULL) {};
pclose (ccproc);
}
}
if (lstat (sunpro_CC, &sb) == 0) {
strcpy (cmd, sunpro_CC);
strcat (cmd, " -V 2>&1");
if ((ccproc = popen (cmd, "r")) != NULL) {
if (fgets (buf, PATH_MAX, ccproc) != NULL) {
vptr = strrchr (buf, 'C');
for (; !isdigit(*vptr); vptr++);
(void) sscanf (vptr, "%d.%d", &cmajor, &cminor);
fprintf (inFile,
"#define DefaultSunProCplusplusCompilerMajorVersion %d\n",
cmajor);
fprintf (inFile,
"#define DefaultSunProCplusplusCompilerMinorVersion %d\n",
cminor);
}
while (fgets (buf, PATH_MAX, ccproc) != NULL) {};
pclose (ccproc);
}
}
}
#endif
#if defined CROSSCOMPILE || defined __GNUC__
static void
get_gcc_version(FILE *inFile, char *name)
{
fprintf (inFile, "#define HasGcc 1\n");
#ifdef CROSSCOMPILE
if (CrossCompiling)
{
if (gnu_c > 1) {
fprintf (inFile, "#define HasGcc2 1\n");
if (gnu_c > 2)
fprintf (inFile, "#define HasGcc3 1\n");
}
fprintf (inFile, "#define GccMajorVersion %d\n", gnu_c);
fprintf (inFile, "#define GccMinorVersion %d\n", gnu_c_minor);
} else
#endif
{
#if __GNUC__ > 1
fprintf (inFile, "#define HasGcc2 1\n");
# if __GNUC__ > 2
fprintf (inFile, "#define HasGcc3 1\n");
# endif
#endif
fprintf (inFile, "#define GccMajorVersion %d\n", __GNUC__);
fprintf (inFile, "#define GccMinorVersion %d\n", __GNUC_MINOR__);
}
#if defined(HAS_MERGE_CONSTANTS)
fprintf (inFile, "#define HasGccMergeConstants %d\n", HAS_MERGE_CONSTANTS);
#endif
}
#endif
static boolean
get_gcc(char *cmd)
{
struct stat sb;
static char* gcc_path[] = {
# if defined(linux) || \
defined(__NetBSD__) || \
defined(__OpenBSD__) || \
defined(__FreeBSD__) || \
defined(__APPLE__) || \
defined(__GNU__)
"/usr/bin/cc",
# endif
"/usr/local/bin/gcc",
"/opt/gnu/bin/gcc",
"/usr/pkg/bin/gcc"
};
#ifdef CROSSCOMPILE
static char* cross_cc_name[] = {
"cc",
"gcc"
};
if (CrossCompiling) {
int i;
for (i = 0; i < sizeof (cross_cc_name) / sizeof cross_cc_name[0]; i++){
strcpy (cmd, CrossCompileDir);
strcat (cmd, "/");
strcat (cmd, cross_cc_name[i]);
if (lstat (cmd, &sb) == 0) {
return TRUE;
break;
}
}
} else
#endif
{
int i;
for (i = 0; i < sizeof (gcc_path) / sizeof gcc_path[0]; i++) {
if (lstat (gcc_path[i], &sb) == 0) {
strcpy (cmd, gcc_path[i]);
return TRUE;
}
}
}
return FALSE;
}
#if defined CROSSCOMPILE || !defined __UNIXOS2__
static void
get_gcc_incdir(FILE *inFile, char* name)
{
FILE* gccproc;
char buf[PATH_MAX];
char cmd[PATH_MAX];
char* ptr;
strcpy(cmd,name);
buf[0] = '\0';
strcat (cmd, " --print-libgcc-file-name");
if ((gccproc = popen (cmd, "r")) != NULL) {
if (fgets (buf, PATH_MAX, gccproc) != NULL) {
ptr = strstr (buf, "libgcc.a");
if (ptr) strcpy (ptr, "include");
}
(void) pclose (gccproc);
}
if (buf[0])
fprintf (inFile, "#define DefaultGccIncludeDir \"%s\"\n", buf);
}
#endif
boolean
define_os_defaults(FILE *inFile)
{
#if defined CROSSCOMPILE || ( !defined(WIN32) && !defined(__UNIXOS2__) )
#ifdef CROSSCOMPILE
if ((sys != win32) && (sys != emx))
#endif
{
# if (defined(DEFAULT_OS_NAME) || defined(DEFAULT_OS_MAJOR_REV) || \
defined(DEFAULT_OS_MINOR_REV) || defined(DEFAULT_OS_TEENY_REV))
struct utsname *name = NULL;
struct utsname uts_name;
char buf[SYS_NMLN * 5 + 1];
#ifdef CROSSCOMPILE
if (!CrossCompiling)
#endif
{
if (uname(&uts_name) < 0)
LogFatal("Cannot invoke uname", "");
else
name = &uts_name;
}
#if defined CROSSCOMPILE && defined linux
else {
strncpy(uts_name.sysname,cross_uts_sysname,SYS_NMLN);
strncpy(uts_name.release,cross_uts_release,SYS_NMLN);
strncpy(uts_name.version,cross_uts_version,SYS_NMLN);
strncpy(uts_name.machine,cross_uts_machine,SYS_NMLN);
name = &uts_name;
}
#endif
# if defined DEFAULT_OS_NAME
# if defined CROSSCOMPILE
if (!CrossCompiling)
# endif
{
parse_utsname(name, DEFAULT_OS_NAME, buf,
"Bad DEFAULT_OS_NAME syntax %s");
# ifdef DEFAULT_OS_NAME_FROB
DEFAULT_OS_NAME_FROB(buf, sizeof buf);
# endif
if (buf[0] != '\0')
fprintf(inFile, "#define DefaultOSName %s\n", buf);
}
# endif
# if defined CROSSCOMPILE
if (CrossCompiling && defaultOsName) {
parse_utsname(name, defaultOsName, buf,
"Bad DEFAULT_OS_NAME syntax %s");
if (defaultOsNameFrob)
defaultOsNameFrob(buf, sizeof buf);
if (buf[0] != '\0')
fprintf(inFile, "#define DefaultOSName %s\n", buf);
}
# endif
# ifdef DEFAULT_OS_MAJOR_REV
# if defined CROSSCOMPILE
if (!CrossCompiling)
# endif
{
parse_utsname(name, DEFAULT_OS_MAJOR_REV, buf,
"Bad DEFAULT_OS_MAJOR_REV syntax %s");
# ifdef DEFAULT_OS_MAJOR_REV_FROB
DEFAULT_OS_MAJOR_REV_FROB(buf, sizeof buf);
# endif
fprintf(inFile, "#define DefaultOSMajorVersion %s\n",
*buf ? trim_version(buf) : "0");
}
# endif
# if defined CROSSCOMPILE
if (CrossCompiling && defaultOsMajorRev) {
parse_utsname(name, defaultOsMajorRev, buf,
"Bad defaultOsMajorRev syntax %s");
if (defaultOsMajorRevFrob)
defaultOsMajorRevFrob(buf, sizeof buf);
fprintf(inFile, "#define DefaultOSMajorVersion %s\n",
*buf ? trim_version(buf) : "0");
}
# endif
# ifdef DEFAULT_OS_MINOR_REV
# if defined CROSSCOMPILE
if (!CrossCompiling)
# endif
{
parse_utsname(name, DEFAULT_OS_MINOR_REV, buf,
"Bad DEFAULT_OS_MINOR_REV syntax %s");
# ifdef DEFAULT_OS_MINOR_REV_FROB
DEFAULT_OS_MINOR_REV_FROB(buf, sizeof buf);
# endif
fprintf(inFile, "#define DefaultOSMinorVersion %s\n",
*buf ? trim_version(buf) : "0");
}
# endif
# if defined CROSSCOMPILE
if (CrossCompiling && defaultOsMinorRev) {
parse_utsname(name, defaultOsMinorRev, buf,
"Bad defaultOsMinorRev syntax %s");
if (defaultOsMinorRevFrob)
defaultOsMinorRevFrob(buf, sizeof buf);
fprintf(inFile, "#define DefaultOSMinorVersion %s\n",
*buf ? trim_version(buf) : "0");
}
# endif
# ifdef DEFAULT_OS_TEENY_REV
# if defined CROSSCOMPILE
if (!CrossCompiling)
# endif
{
parse_utsname(name, DEFAULT_OS_TEENY_REV, buf,
"Bad DEFAULT_OS_TEENY_REV syntax %s");
# ifdef DEFAULT_OS_TEENY_REV_FROB
DEFAULT_OS_TEENY_REV_FROB(buf, sizeof buf);
# endif
fprintf(inFile, "#define DefaultOSTeenyVersion %s\n",
*buf ? trim_version(buf) : "0");
}
# endif
# if defined CROSSCOMPILE
if (CrossCompiling && defaultOsTeenyRev) {
parse_utsname(name, defaultOsTeenyRev, buf,
"Bad defaultOsTeenyRev syntax %s");
if (defaultOsTeenyRevFrob)
defaultOsTeenyRevFrob(buf, sizeof buf);
fprintf(inFile, "#define DefaultOSTeenyVersion %s\n",
*buf ? trim_version(buf) : "0");
}
# endif
# ifdef DEFAULT_MACHINE_ARCHITECTURE
# if defined CROSSCOMPILE
if (!CrossCompiling)
# endif
{
parse_utsname(name, DEFAULT_MACHINE_ARCHITECTURE, buf,
"Bad DEFAULT_MACHINE_ARCHITECTURE %s");
fprintf(inFile, "#ifndef %s\n# define %s\n#endif\n", buf, buf);
}
# endif
# if defined CROSSCOMPILE
if (CrossCompiling && defaultMachineArchitecture) {
parse_utsname(name, defaultMachineArchitecture, buf,
"Bad defaultMachineArchitecture syntax %s");
fprintf(inFile, "#ifndef %s\n# define %s\n#endif\n", buf, buf);
}
# endif
# endif
# if defined CROSSCOMPILE
if (CrossCompiling)
get_cross_compile_dir(inFile);
else
# endif
fprintf(inFile, "#define CrossCompiling NO\n");
# if defined CROSSCOMPILE
if (CrossCompiling && sys == LinuX)
# endif
# if defined CROSSCOMPILE || defined linux
# ifdef CROSSCOMPILE
if (sys == LinuX)
# endif
get_distrib (inFile);
# endif
# if defined linux
# if defined CROSSCOMPILE
if (!CrossCompiling)
# endif
get_libc_version (inFile);
# if defined CROSSCOMPILE
else {
fprintf(inFile,"#define DefaultLinuxCLibMajorVersion %d\n",
glibc_major);
fprintf(inFile,"#define DefaultLinuxCLibMinorVersion %d\n",
glibc_minor);
fprintf(inFile,"#define DefaultLinuxCLibTeenyVersion 0\n");
}
# endif
# endif
# if defined CROSSCOMPILE || defined linux
# if defined CROSSCOMPILE
if (sys == LinuX)
# endif
get_ld_version(inFile);
# endif
# if defined (sun) && defined(SVR4)
get_sun_compiler_versions (inFile);
# endif
# if defined CROSSCOMPILE || defined __GNUC__
# if defined CROSSCOMPILE
if (gnu_c)
# endif
{
char name[PATH_MAX];
if (get_gcc(name)) {
get_gcc_version (inFile,name);
# if defined CROSSCOMPILE || !defined __UNIXOS2__
# if defined CROSSCOMPILE
if (sys != emx)
# endif
get_gcc_incdir(inFile,name);
# endif
}
}
# endif
# if defined __FreeBSD__
# if defined CROSSCOMPILE
if (sys == freeBSD)
# endif
get_binary_format(inFile);
# endif
}
#endif
#if defined WIN32
# ifdef CROSSCOMPILE
else if (sys == win32 && !CrossCompiling)
# endif
{
OSVERSIONINFO osvi;
static char* os_names[] = { "Win32s", "Windows 95", "Windows NT" };
memset(&osvi, 0, sizeof(OSVERSIONINFO));
osvi.dwOSVersionInfoSize = sizeof (OSVERSIONINFO);
GetVersionEx (&osvi);
fprintf (inFile, "#define DefaultOSName Microsoft %s\n",
os_names[osvi.dwPlatformId]);
fprintf(inFile, "#define DefaultOSMajorVersion %d\n", osvi.dwMajorVersion);
fprintf(inFile, "#define DefaultOSMinorVersion %d\n", osvi.dwMinorVersion);
fprintf(inFile, "#define DefaultOSTeenyVersion %d\n",
osvi.dwBuildNumber & 0xFFFF);
}
#endif
#ifdef CROSSCOMPILE
else if (sys == emx)
#endif
#if defined CROSSCOMPILE || defined __UNIXOS2__
{
fprintf(inFile, "#define DefaultOSMajorVersion 4\n");
fprintf(inFile, "#define DefaultOSMinorVersion 0\n");
fprintf(inFile, "#define DefaultOSTeenyVersion 0\n");
}
#endif
#if defined(__OpenBSD__)
get_stackprotector(inFile);
#endif
return FALSE;
}
void
cppit(char *imakefile, char *template, char *masterc,
FILE *outfd, char *outfname)
{
FILE *inFile;
haveImakefileC = TRUE;
inFile = fopen(masterc, "w");
if (inFile == NULL)
LogFatal("Cannot open %s for output.", masterc);
if (fprintf(inFile, "%s\n", ImakefileCHeader) < 0 ||
define_os_defaults(inFile) ||
optional_include(inFile, "IMAKE_LOCAL_DEFINES", "localdefines") ||
optional_include(inFile, "IMAKE_ADMIN_DEFINES", "admindefines") ||
fprintf(inFile, "#define %s <%s>\n", ImakeDefSym, imakefile) < 0 ||
fprintf(inFile, LocalDefineFmt, ImakeTmplSym, template) < 0 ||
fprintf(inFile, IncludeFmt, ImakeTmplSym) < 0 ||
optional_include(inFile, "IMAKE_ADMIN_MACROS", "adminmacros") ||
optional_include(inFile, "IMAKE_LOCAL_MACROS", "localmacros") ||
fflush(inFile) ||
fclose(inFile))
LogFatal("Cannot write to %s.", masterc);
doit(outfd, cpp, cpp_argv);
CleanCppOutput(outfd, outfname);
}
void
makeit(void)
{
doit(NULL, make_argv[0], make_argv);
}
char *
CleanCppInput(char *imakefile)
{
FILE *outFile = NULL;
FILE *inFile;
char *buf,
*pbuf,
*punwritten,
*ptoken,
*pend,
savec;
int count;
struct stat st;
if (!(inFile = fopen(imakefile, "r")))
LogFatal("Cannot open %s for input.", imakefile);
if (fstat(fileno(inFile), &st) < 0)
LogFatal("Cannot stat %s for size.", imakefile);
buf = Emalloc((int)st.st_size+3);
count = fread(buf + 2, 1, st.st_size, inFile);
if (count == 0 && st.st_size != 0)
LogFatal("Cannot read %s:", imakefile);
fclose(inFile);
buf[0] = '\n';
buf[1] = '\n';
buf[count + 2] = '\0';
punwritten = pbuf = buf + 2;
while (*pbuf) {
if (*pbuf == '#' && pbuf[-1] == '\n' && pbuf[-2] != '\\') {
ptoken = pbuf+1;
while (*ptoken == ' ' || *ptoken == '\t')
ptoken++;
pend = ptoken;
while (*pend && *pend != ' ' && *pend != '\t' && *pend != '\n' && *pend != '\r')
pend++;
savec = *pend;
*pend = '\0';
if (strcmp(ptoken, "define") &&
strcmp(ptoken, "if") &&
strcmp(ptoken, "ifdef") &&
strcmp(ptoken, "ifndef") &&
strcmp(ptoken, "include") &&
strcmp(ptoken, "line") &&
strcmp(ptoken, "else") &&
strcmp(ptoken, "elif") &&
strcmp(ptoken, "endif") &&
strcmp(ptoken, "error") &&
strcmp(ptoken, "pragma") &&
strcmp(ptoken, "undef")) {
if (outFile == NULL) {
#ifdef HAS_MKSTEMP
int fd;
#endif
tmpImakefile = Strdup(tmpImakefile);
#ifndef HAS_MKSTEMP
if (mktemp(tmpImakefile) == NULL ||
(outFile = fopen(tmpImakefile, "w+")) == NULL) {
LogFatal("Cannot open %s for write.",
tmpImakefile);
}
#else
fd=mkstemp(tmpImakefile);
if (fd != -1)
outFile = fdopen(fd, "w");
if (outFile == NULL) {
if (fd != -1) {
unlink(tmpImakefile); close(fd);
}
LogFatal("Cannot open %s for write.",
tmpImakefile);
}
#endif
}
writetmpfile(outFile, punwritten, pbuf-punwritten,
tmpImakefile);
if (ptoken > pbuf + 1)
writetmpfile(outFile, "XCOMM", 5, tmpImakefile);
else
writetmpfile(outFile, "XCOMM ", 6, tmpImakefile);
punwritten = pbuf + 1;
}
*pend = savec;
}
pbuf++;
}
if (outFile) {
writetmpfile(outFile, punwritten, pbuf-punwritten, tmpImakefile);
fclose(outFile);
return tmpImakefile;
}
return(imakefile);
}
void
CleanCppOutput(FILE *tmpfd, char *tmpfname)
{
char *input;
int blankline = 0;
while((input = ReadLine(tmpfd, tmpfname))) {
if (isempty(input)) {
if (blankline++)
continue;
#ifdef CROSSCOMPILE
if (fixup_whitespace)
#endif
#if defined CROSSCOMPILE || defined FIXUP_CPP_WHITESPACE
KludgeResetRule();
#endif
} else {
blankline = 0;
#ifdef CROSSCOMPILE
if (fixup_whitespace)
#endif
#if defined CROSSCOMPILE || defined FIXUP_CPP_WHITESPACE
KludgeOutputLine(&input);
#endif
writetmpfile(tmpfd, input, strlen(input), tmpfname);
}
writetmpfile(tmpfd, "\n", 1, tmpfname);
}
fflush(tmpfd);
#ifdef NFS_STDOUT_BUG
ftruncate (fileno(tmpfd), (off_t)ftell(tmpfd));
#endif
}
boolean
isempty(char *line)
{
char *pend;
if (*line == '#') {
pend = line+1;
if (*pend == ' ')
pend++;
if (*pend == 'l' && pend[1] == 'i' && pend[2] == 'n' &&
pend[3] == 'e' && pend[4] == ' ')
pend += 5;
if (isdigit(*pend)) {
do {
pend++;
} while (isdigit(*pend));
if (*pend == '\n' || *pend == '\0')
return(TRUE);
if (*pend++ == ' ' && *pend == '"')
return(TRUE);
}
while (*pend)
pend++;
} else {
for (pend = line; *pend; pend++) {
if (*pend == 'X' && pend[1] == 'C' && pend[2] == 'O' &&
pend[3] == 'M' && pend[4] == 'M' &&
(pend == line || pend[-1] == ' ' || pend[-1] == '\t' || pend[-1] == '\r') &&
(pend[5] == ' ' || pend[5] == '\t' || pend[5] == '\r' || pend[5] == '\0'))
{
*pend = '#';
memmove(pend+1, pend+5, strlen(pend+5)+1);
}
#ifdef CROSSCOMPILE
if (magic_make_vars)
#endif
{
#if defined CROSSCOMPILE || defined MAGIC_MAKE_VARS
if (*pend == 'X' && pend[1] == 'V' && pend[2] == 'A' &&
pend[3] == 'R')
{
char varbuf[5];
int i;
if (pend[4] == 'd' && pend[5] == 'e' && pend[6] == 'f' &&
pend[7] >= '0' && pend[7] <= '9')
{
i = pend[7] - '0';
sprintf(varbuf, "%0.4d", xvariable);
strncpy(pend+4, varbuf, 4);
xvariables[i] = xvariable;
xvariable = (xvariable + 1) % 10000;
}
else if (pend[4] == 'u' && pend[5] == 's' &&
pend[6] == 'e' && pend[7] >= '0' &&
pend[7] <= '9')
{
i = pend[7] - '0';
sprintf(varbuf, "%0.4d", xvariables[i]);
strncpy(pend+4, varbuf, 4);
}
}
#endif
}
}
}
while (--pend >= line && (*pend == ' ' || *pend == '\t' || *pend == '\r')) ;
pend[1] = '\0';
return (*line == '\0');
}
char *
ReadLine(FILE *tmpfd, char *tmpfname)
{
static boolean initialized = FALSE;
static char *buf, *pline, *end;
register char *p1, *p2;
if (! initialized) {
#ifdef WIN32
FILE *fp = tmpfd;
#endif
int total_red;
struct stat st;
fseek(tmpfd, 0, 0);
if (fstat(fileno(tmpfd), &st) < 0)
LogFatal("cannot stat %s for size", tmpMakefile);
pline = buf = Emalloc((int)st.st_size+1);
total_red = fread(buf, 1, st.st_size, tmpfd);
if (total_red == 0 && st.st_size != 0)
LogFatal("cannot read %s", tmpMakefile);
end = buf + total_red;
*end = '\0';
fseek(tmpfd, 0, 0);
#if defined(SYSV) || defined(WIN32) || defined(USE_FREOPEN)
tmpfd = freopen(tmpfname, "w+", tmpfd);
#ifdef WIN32
if (! tmpfd)
tmpfd = freopen(tmpfname, "w+", fp);
#endif
if (! tmpfd)
LogFatal("cannot reopen %s\n", tmpfname);
#else
ftruncate(fileno(tmpfd), (off_t) 0);
#endif
initialized = TRUE;
fprintf (tmpfd, "# Makefile generated by imake - do not edit!\n");
fprintf (tmpfd, "# %s\n",
"$Xorg: imake.c,v 1.6 2001/02/09 02:03:15 xorgcvs Exp $");
}
for (p1 = pline; p1 < end; p1++) {
if (*p1 == '@' && *(p1+1) == '@'
&& !(p1 != pline && !isspace(*(p1-1)) && *(p1+2) == '/'))
{
*p1++ = '\0';
p1++;
break;
}
else if (*p1 == '\n') {
#if defined CROSSCOMPILE || defined WIN32
# if defined CROSSCOMPILE
if (sys == win32)
# endif
{
if (p1 > pline && p1[-1] == '\r')
p1[-1] = '\0';
}
#endif
*p1++ = '\0';
break;
}
}
p2 = (pline == p1 ? NULL : pline);
pline = p1;
return(p2);
}
void
writetmpfile(FILE *fd, char *buf, int cnt, char *fname)
{
if (fwrite(buf, sizeof(char), cnt, fd) == -1)
LogFatal("Cannot write to %s.", fname);
}
char *
Emalloc(int size)
{
char *p;
if ((p = malloc(size)) == NULL)
LogFatalI("Cannot allocate %d bytes", size);
return(p);
}
#if defined CROSSCOMPILE || defined FIXUP_CPP_WHITESPACE
void
KludgeOutputLine(char **pline)
{
char *p = *pline;
char quotechar = '\0';
switch (*p) {
case '#':
break;
case '\t':
break;
case ' ':
default:
#ifdef CROSSCOMPILE
if (inline_syntax)
#endif
#if defined CROSSCOMPILE || defined INLINE_SYNTAX
{
if (*p == '<' && p[1] == '<') {
InInline--;
InRule = TRUE;
break;
}
}
#endif
for (; *p; p++) {
if (quotechar) {
if (quotechar == '\\' ||
(*p == quotechar &&
# if defined CROSSCOMPILE || defined WIN32
(
# if defined CROSSCOMPILE
(sys == win32) &&
# endif
quotechar != ')') &&
# endif
p[-1] != '\\'))
quotechar = '\0';
continue;
}
switch (*p) {
case '\\':
case '"':
case '\'':
quotechar = *p;
break;
case '(':
quotechar = ')';
break;
case '{':
quotechar = '}';
break;
case '[':
quotechar = ']';
break;
case '=':
#ifdef CROSSCOMPILE
if (remove_cpp_leadspace)
#endif
#if defined CROSSCOMPILE || defined REMOVE_CPP_LEADSPACE
{
if (!InRule && **pline == ' ') {
while (**pline == ' ')
(*pline)++;
}
}
#endif
goto breakfor;
#if defined CROSSCOMPILE || defined INLINE_SYNTAX
case '<':
if (inline_syntax) {
if (p[1] == '<')
InInline++;
}
break;
#endif
case ':':
if (p[1] == '=')
goto breakfor;
while (**pline == ' ')
(*pline)++;
InRule = TRUE;
return;
}
}
breakfor:
if (InRule && **pline == ' ')
**pline = '\t';
break;
}
}
void
KludgeResetRule(void)
{
InRule = FALSE;
}
#endif
char *
Strdup(char *cp)
{
char *new = Emalloc(strlen(cp) + 1);
strcpy(new, cp);
return new;
}
#ifdef CROSSCOMPILE
char*
CrossCompileCPP(void)
{
char *cpp, *c;
int len ;
if (crosscompile_use_cc_e)
AddCppArg("-E");
cpp = strrchr(crosscompile_cpp,'/');
if (!cpp)
cpp = crosscompile_cpp;
else
cpp++;
len = strlen(cpp) + strlen(CrossCompileDir) + 2;
c = Emalloc(len);
(void)snprintf(c, len,"%s/%s",CrossCompileDir,cpp);
return c;
}
#endif
#ifdef CROSSCOMPILE
static void
get_cross_compile_dir(FILE *inFile)
{
fprintf(inFile, "#define CrossCompileDir %s\n",
CrossCompileDir);
fprintf(inFile, "#define CrossCompiling YES\n");
}
#endif