#include <stdio.h>
#include <stdlib.h>
#include <modes.h>

extern FILE *__firstfile,*__lastfile;


FILE *__open_file(const char *name,const char *mode,FILE *f)
{
  int append=0,truncate=0,fh;
  const char *om=mode;
  unsigned char os9mode=0;

  f->count = 0;
  f->base = 0;
  f->bufsize = 0;
  f->prev = 0;
  f->next = 0;
  switch (*mode++) {
    case 'a': append=1; os9mode=S_IWRITE; f->flags=_WRITEABLE; break;
    case 'r': os9mode=S_IREAD; f->flags=_READABLE; break;
    case 'w': truncate=1; os9mode=S_IWRITE; f->flags=_WRITEABLE; break;
    default: goto file_err;
  }
  if (*mode == 'b') mode++;
#ifdef _CLE
  else f->flags |= _CLE;
  f->clebuf = -1;
#endif
  if (*mode == '+') {
    os9mode |= S_IREAD|S_IWRITE;
    f->flags |= _READABLE|_WRITEABLE;
  }
  if (!truncate)
    if ((fh = open(name,os9mode)) == -1)
      if (!(truncate = append))
        goto file_err;
  if (truncate) {
    if ((fh = creat(name,os9mode)) == -1) {
      file_err:
      free(f);
      return 0;
    }
  }
  f->filehandle = fh;
#if HAVE_TTYS
  if (__isatty(fh)) {
    f->flags |= _LINEBUF|_ISTTY;
  }
#endif
  if (__lastfile) {
    __lastfile->next = f;
    f->prev = __lastfile;
    __lastfile = f;
  }
  else{
    __firstfile = __lastfile = f;
  }
  if (append) lseek(fh,0,SEEK_END);
  return f;
}


FILE *fopen(const char *name,const char *mode)
{
  FILE *f;

  if (!(f = malloc(sizeof(FILE)))) return 0;
  return __open_file(name,mode,f);
}


void _EXIT_2_fopen(void)
{
  while(__firstfile && !fclose(__firstfile));  /* close all open files */
}
