Milán Major

netscape-revival

1 branch
Code

sun-java/java/java_stub.c

/*
 * @(#)javai.c	1.75 95/08/11
 *
 * Copyright (c) 1994 Sun Microsystems, Inc. All Rights Reserved.
 *
 * Permission to use, copy, modify, and distribute this software
 * and its documentation for NON-COMMERCIAL purposes and without
 * fee is hereby granted provided that this copyright notice
 * appears in all copies. Please refer to the file "copyright.html"
 * for further important copyright and licensing information.
 *
 * SUN MAKES NO REPRESENTATIONS OR WARRANTIES ABOUT THE SUITABILITY OF
 * THE SOFTWARE, EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED
 * TO THE IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS FOR A
 * PARTICULAR PURPOSE, OR NON-INFRINGEMENT. SUN SHALL NOT BE LIABLE FOR
 * ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF USING, MODIFYING OR
 * DISTRIBUTING THIS SOFTWARE OR ITS DERIVATIVES.
 */

/*-
 *      interpret an java object file
 */

#include <stdio.h>
#include <sys/types.h>
#include <sys/stat.h>

#include "javaThreads.h"
#include "errno.h"
#include "tree.h"
#include "oobj.h"
#include "interpreter.h"
#include "exceptions.h"
#include "javaString.h"
#include "log.h"
#include "installpath.h"
#include "bool.h"

#ifndef NATIVE
#include "iomgr.h"
#include <fcntl.h>
#ifndef XP_PC
#include <sys/wait.h>
#include <unistd.h>
#include <sys/signal.h>
#endif /* ! WIN32 */
#include <signal.h>
#else /* NATIVE  */
#include "monitor.h"
#endif /* NATIVE */

#if defined(XP_PC) && !defined(_WIN32)
#include "jrtpcos.h"
#endif

void
Execute(char **command, char *alternate);

/* OpenCode for the interpreter.

   Tries to open a code file (fn).  That is, a .class file.  This
   returns -1 if the specified file can be opened but cannot be
   stat'd.  REMIND: When can that happen?  It returns -2 if the
   file cannot be opened.  Otherwise, it returns a valid file
   descriptor. If SkipSourceChecks is true, then we return at that
   point.

   Otherwise, we try to recompile the source.  If fn == 0, then we
   use sfn as the source file name to use.  sfn is specified by
   LoadFile by using the source hint associated with the import
   statement, or by the source file name as extracted from the
   previously recompiled version of this class.  That only happens
   if LoadFile already successfully loaded the class, and then
   noticed that the source is more recent than the .class file it
   opened.

   If sfn is 0 then a source file name is constructed by stripping
   the ".class" off of fn and replacing it with .java.  This often
   doesn't work, because .class files can be put in difference
   directories from their source files, but it's a good guess
   sometimes.  Then javac is forked to recompile the class, and
   the resulting .class file is opened.

   In summary, OpenCode for the interpreter returns a file
   descriptor for a compiler .class file.  If it can't open the
   .class file, it forks the compiler to compile some source so
   that the .class file will be there.  If after all that there is
   still no .class file, it gives up and returns -2.

   If st == 0, then doesn't even bother trying to open the file.
   Instead, it just does the source file thing. */

#ifndef XP_PC
int
OpenCode(char *fn, char *sfn, char *dir, struct stat * st)
{
    long fd = -1;
    char srcname[300];
    char sccsname[300];
    long mtime;
    struct stat srcst, sccsst;
    char *src, *dst;

#ifndef XP_PC
    if (st != 0 && fn != 0 && (fd = open(fn, O_RDONLY, 0644)) >= 0
#else
    if (st != 0 && fn != 0 && (fd = open(fn, O_RDONLY|O_BINARY, 0644)) >= 0
#endif
	    && fstat(fd, st) < 0) {
	close(fd);
	fd = -1;
    }
    if (SkipSourceChecks)
	return fd < 0 ? -2 : fd;
    dst = srcname;
    *dst++ = '-';
    *dst++ = 'G';
    if (sfn == 0) {
	sysAssert(fn);
	for ((src = fn); (*dst++ = *src++););
	if (dst - srcname < 3 + JAVAOBJEXTLEN
		|| strcmp(dst - JAVAOBJEXTLEN - 2,
			  "." JAVAOBJEXT) != 0)
	    return fd < 0 ? -2 : fd;
	dst -= JAVAOBJEXTLEN + 2;
	strcpy(dst, "." JAVASRCEXT);
    } else {
	for ((src = sfn); (*dst++ = *src++););
    }
    while (dst > srcname + 2 && dst[-1] != '/')
	dst--;
    strncpy(sccsname, srcname + 2, dst - srcname);
    strncpy(sccsname + (dst - srcname - 2), "SCCS/s.", 7);
    strcpy(sccsname + (dst - srcname) + 5, dst);
    mtime = ((fd < 0 && fn) || st == 0) ? 0 : st->st_mtime;
    if (stat(srcname + 2, &srcst) < 0)
	srcst.st_mtime = 0;
    if (stat(sccsname, &sccsst) < 0)
	sccsst.st_mtime = 0;
    if (srcst.st_mtime > mtime
	    || sccsst.st_mtime > mtime) {
	char *com[30];
	char **comp = com;
	if (fd >= 0) {
	    close(fd);
	    fd = -1;
	}
	if (sccsst.st_mtime > srcst.st_mtime) {
	    com[0] = "/usr/sccs/get";
	    com[1] = sccsname;
	    com[2] = srcname;
	    com[3] = 0;
	    Execute(com, 0);
	}
#ifdef DEBUG
	*comp++ = "javac_g";
#else
	*comp++ = "javac";
#endif
	if (verbose)
	    *comp++ = "-verbose";
	if (dir) {
	    *comp++ = "-d";
	    *comp++ = dir;
	}
	*comp++ = srcname+2;
	*comp = 0;
	{
	    char    path[256];
	    char    *alt = 0;
	    char    *ep;


	    if ((ep = getenv("JAVA_HOME")) == 0)
		alt = 0;
	    else {
		sprintf(path, "%s/bin/", ep);
#ifdef DEBUG
		strcat(path, "javac_g");
#else
		strcat(path, "javac");
#endif
		alt = path;
	    }
	    Execute(com, alt);
	}
	if (fn) {
#ifndef XP_PC
	    fd = open(fn, 0, 0644);
#else
	    fd = open(fn, O_BINARY, 0644);
#endif
	    if (fd >= 0 && st)
		if (fstat(fd, st) < 0) {
		    close(fd);
		    fd = -1;
		}
	}
    }
    return fd < 0 ? -2 : fd;
}

void
ClassDefHook(ClassClass *cb)
{
}
#endif    /* ! XP_PC */

extern JAVA_PUBLIC_API(int) start_java(int argc, char **argv);

#if !defined(XP_PC) || defined(_WIN32)

int
main(int argc, char **argv)
{
    return start_java(argc, argv);
}

#else

extern int
JRTPC_StartJava(int argc, char *(argv[]));

FILE *output;

static void
WriteStandardOut(const char *string)
{
	fwrite(string, sizeof(char), strlen(string), output);
	fflush(output);
}

int PASCAL 
WinMain(HINSTANCE hinstCurrent, HINSTANCE hinstPrevious,
    LPSTR lpszCmdLine, int nCmdShow)
{
	extern int __argc;
	extern char ** __argv;
	int	   ac;
	char **av;
	int	   javaExitCode;
	HINSTANCE lib;

	ac = __argc;
	av = __argv;

	if (ac >2) {
		if (strcmp(av[1],"-o") == 0) {
			output = fopen(av[2],"w");
			if (output) {
				JRTPC_SetClientOutputCallback( WriteStandardOut );
				ac -= 2;
				av += 2;
			}
		}
	}

	lib = JRTPC_Init(NULL);
	javaExitCode = JRTPC_StartJava(ac, av);
        if (output != NULL)
           fclose(output);
        if (lib != (HINSTANCE) NULL)
		FreeLibrary(lib);
	return javaExitCode;
}

#endif