
/* Readline interface for tokenizer.c and [raw_]input() in bltinmodule.c.
   By default, or when stdin is not a tty device, we have a super
   simple my_readline function using fgets.
   Optionally, we can use the GNU readline library.
   my_readline() has a different return value from GNU readline():
   - NULL if an interrupt occurred or if an error occurred
   - a malloc'ed empty string if EOF was read
   - a malloc'ed string ending in \n normally
*/

#include "Python.h"
#ifdef MS_WINDOWS
#define WIN32_LEAN_AND_MEAN
#include "windows.h"
#endif /* MS_WINDOWS */

#ifdef __VMS
extern char* vms__StdioReadline(FILE *sys_stdin, FILE *sys_stdout, char *prompt);
#endif


PyThreadState* _PyOS_ReadlineTState;

#ifdef WITH_THREAD
#include "pythread.h"
static PyThread_type_lock _PyOS_ReadlineLock = NULL;
#endif

int (*PyOS_InputHook)(void) = NULL;

#ifdef RISCOS
int Py_RISCOSWimpFlag;
#endif

/* This function restarts a fgets() after an EINTR error occurred
   except if PyOS_InterruptOccurred() returns true. */

static int
my_fgets(char *buf, int len, FILE *fp)
{
	char *p;
	for (;;) {
		if (PyOS_InputHook != NULL)
			(void)(PyOS_InputHook)();
		errno = 0;
		p = fgets(buf, len, fp);
		if (p != NULL)
			return 0; /* No error */
#ifdef MS_WINDOWS
		/* In the case of a Ctrl+C or some other external event 
		   interrupting the operation:
		   Win2k/NT: ERROR_OPERATION_ABORTED is the most recent Win32 
		   error code (and feof() returns TRUE).
		   Win9x: Ctrl+C seems to have no effect on fgets() returning
		   early - the signal handler is called, but the fgets()
		   only returns "normally" (ie, when Enter hit or feof())
		*/
		if (GetLastError()==ERROR_OPERATION_ABORTED) {
			/* Signals come asynchronously, so we sleep a brief 
			   moment before checking if the handler has been 
			   triggered (we cant just return 1 before the 
			   signal handler has been called, as the later 
			   signal may be treated as a separate interrupt).
			*/
			Sleep(1);
			if (PyOS_InterruptOccurred()) {
				return 1; /* Interrupt */
			}
			/* Either the sleep wasn't long enough (need a
			   short loop retrying?) or not interrupted at all
			   (in which case we should revisit the whole thing!)
			   Logging some warning would be nice.  assert is not
			   viable as under the debugger, the various dialogs
			   mean the condition is not true.
			*/
		}
#endif /* MS_WINDOWS */
		if (feof(fp)) {
			return -1; /* EOF */
		}
#ifdef EINTR
		if (errno == EINTR) {
			int s;
			PyEval_RestoreThread(_PyOS_ReadlineTState);
			s = PyErr_CheckSignals();
			PyThreadState_Swap(NULL);
			if (s < 0) {
				return 1;
			}
		}
#endif
		if (PyOS_InterruptOccurred()) {
			return 1; /* Interrupt */
		}
		return -2; /* Error */
	}
	/* NOTREACHED */
}


/* Readline implementation using fgets() */

char *
PyOS_StdioReadline(FILE *sys_stdin, FILE *sys_stdout, char *prompt)
{
	size_t n;
	char *p;
	n = 100;
	if ((p = PyMem_MALLOC(n)) == NULL)
		return NULL;
	fflush(sys_stdout);
#ifndef RISCOS
	if (prompt)
		fprintf(stderr, "%s", prompt);
#else
	if (prompt) {
		if(Py_RISCOSWimpFlag)
			fprintf(stderr, "\x0cr%s\x0c", prompt);
		else
			fprintf(stderr, "%s", prompt);
	}
#endif
	fflush(stderr);
	switch (my_fgets(p, (int)n, sys_stdin)) {
	case 0: /* Normal case */
		break;
	case 1: /* Interrupt */
		PyMem_FREE(p);
		return NULL;
	case -1: /* EOF */
	case -2: /* Error */
	default: /* Shouldn't happen */
		*p = '\0';
		break;
	}
	n = strlen(p);
	while (n > 0 && p[n-1] != '\n') {
		size_t incr = n+2;
		p = PyMem_REALLOC(p, n + incr);
		if (p == NULL)
			return NULL;
		if (incr > INT_MAX) {
			PyErr_SetString(PyExc_OverflowError, "input line too long");
		}
		if (my_fgets(p+n, (int)incr, sys_stdin) != 0)
			break;
		n += strlen(p+n);
	}
	return PyMem_REALLOC(p, n+1);
}


/* By initializing this function pointer, systems embedding Python can
   override the readline function.

   Note: Python expects in return a buffer allocated with PyMem_Malloc. */

char *(*PyOS_ReadlineFunctionPointer)(FILE *, FILE *, char *);


/* Interface used by tokenizer.c and bltinmodule.c */

char *
PyOS_Readline(FILE *sys_stdin, FILE *sys_stdout, char *prompt)
{
	char *rv;

	if (_PyOS_ReadlineTState == PyThreadState_GET()) {
		PyErr_SetString(PyExc_RuntimeError,
				"can't re-enter readline");
		return NULL;
	}
	

	if (PyOS_ReadlineFunctionPointer == NULL) {
#ifdef __VMS
                PyOS_ReadlineFunctionPointer = vms__StdioReadline;
#else
                PyOS_ReadlineFunctionPointer = PyOS_StdioReadline;
#endif
	}
	
#ifdef WITH_THREAD
	if (_PyOS_ReadlineLock == NULL) {
		_PyOS_ReadlineLock = PyThread_allocate_lock();		
	}
#endif

	_PyOS_ReadlineTState = PyThreadState_GET();
	Py_BEGIN_ALLOW_THREADS
#ifdef WITH_THREAD
	PyThread_acquire_lock(_PyOS_ReadlineLock, 1);
#endif

        /* This is needed to handle the unlikely case that the
         * interpreter is in interactive mode *and* stdin/out are not
         * a tty.  This can happen, for example if python is run like
         * this: python -i < test1.py
         */
        if (!isatty (fileno (sys_stdin)) || !isatty (fileno (sys_stdout)))
                rv = PyOS_StdioReadline (sys_stdin, sys_stdout, prompt);
        else
                rv = (*PyOS_ReadlineFunctionPointer)(sys_stdin, sys_stdout,
                                                     prompt);
	Py_END_ALLOW_THREADS

#ifdef WITH_THREAD
	PyThread_release_lock(_PyOS_ReadlineLock);
#endif

	_PyOS_ReadlineTState = NULL;

	return rv;
}
