#include <stdio.h>
#include <stdlib.h>
#include <fcntl.h>
#include <sys/dir.h>
#include <sys/stat.h>
#define DEFAULT_SIZE 1024
#define ShowError(a) ShowErrorFunc(__LINE__,a)

#ifndef O_BINARY
#define O_BINARY 0
#endif

void ShowErrorFunc (int line,char *s);

static char* _ver="$VER: Asplit 2.03";

extern int errno;

void ShowErrorFunc(int line,char *s)
{
  fprintf(stderr,"%s: Error on line %d,",s,line);
  perror("");
  exit(errno);
}


void usage(char *s)
{
  fprintf(stderr,"%s by MENDEZ Marc. (%s %s) All right reserved. Copyright 1994\n",s,__DATE__,__TIME__);
  fprintf(stderr,"Usage: %s [-b buffer] [-n number] -s size filein [fileout|directory]\n",s);
  exit(1);
}

char * basename(char *Path)
{
  char *p,*t ;
  
  if ((p=strrchr(Path,'/'))==NULL)
    p=strrchr(Path,':');
  
  p = (p==NULL ? Path : p+1);
  if ((t=(char *)malloc(strlen(p)+1))==NULL)
    ShowError("malloc");
  
  strcpy(t,p);
  return t;
}

int OpenOutputFile(char *root, int num,char *StrTemplate)
{
  int Ptr;
  char *EffectiveFileNameOut;  

#ifndef AMIGA
  int mask;
  
  umask(mask=umask(0));
  mask=(~mask)&(S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP|S_IROTH|S_IWOTH);
  
#endif
  
  if ((EffectiveFileNameOut=(char*)malloc(sizeof(char)*(MAXNAMLEN+1)))==NULL)
    ShowError("malloc");

  sprintf(EffectiveFileNameOut,StrTemplate,root,num);

#ifndef AMIGA
  if ( (Ptr =
	open(EffectiveFileNameOut,O_WRONLY|O_CREAT|O_TRUNC|O_BINARY,mask))<0)  
#else
  if ( (Ptr =
	open(EffectiveFileNameOut,O_WRONLY|O_CREAT|O_TRUNC|O_BINARY))<0)  
#endif
    ShowError("open");

  free(EffectiveFileNameOut);
  return Ptr;
  
}


int main(int argc, char *argv[])
{
  int In, Out;
  long Size=0;
  char *Buffer;
  long BufferSize=DEFAULT_SIZE;
  char *FileNameIn=NULL, *FileNameOut=NULL;
  struct stat StatBuffer;
  
  int i=1;
  int NumberOfCharRead;
  int NumberOfCharToRead;
  long FileNumber=0;
  long FileNumberBase=0;
  
  long NumberMaxOfFile;
  char *StringTemplate;
  

  if (argc==1)
    usage(argv[0]);
  

  while (i<=(argc-1))
    {
      switch(argv[i][0])
	{
	case '-':
	  {
	    switch(argv[i][1])
	      {
	      case 'b':
		{
		  long t;
		  if (i+1>(argc-1))
		    usage(argv[0]);
		  if ((t=atol(argv[i+1]))<=0)
		    usage(argv[0]);
		  BufferSize=t;
		  i++;
		  break;
		}		/* case 'b' */
	      case 's':
		{
		  long t;
		  if (i+1>(argc-1))
		    usage(argv[0]);
		  if ((t=atol(argv[i+1]))<=0)
		    usage(argv[0]);
		  Size=t;
		  i++;		
		  break;
		}		/* case 's' */
	      case 'n':
		{
		  if (i+1>(argc-1))
		    usage(argv[0]);
		  if ((FileNumberBase = atol (argv[i+1]))<0)
		      usage(argv[0]);
		  i++;
		  break;
		} /* case 'n' */
	      default:
		  usage(argv[0]);
				/* default */
	      }			/* switch(argv[i][1]) */
	    break;
	  }			/* case '-' */
	default:
	  {
	    char *t;
	    if ((t=(char*)strdup(argv[i]))==NULL)
	      ShowError(argv[0]);

	    if (FileNameIn==NULL)
	      {
		if ((FileNameIn=(char*)strdup(t))==NULL)
		  ShowError(argv[0]);
	      }
	    else
	      {
		if (FileNameOut==NULL)
		  {
		    if ((FileNameOut=(char*)strdup(t))==NULL)
		      ShowError(argv[0]);
		  }
		else
		  usage(argv[0]);
	      }
	    free(t);
	    break;
	  }			/* default: */
	}			/* switch(argv[i][0]) */
      i++;
    }				/* while (i<=argc) */

  if (FileNameOut==NULL && FileNameIn==NULL)
    usage(argv[0]);
  

  if (FileNameOut==NULL)
    {
      char *t;
      
      if ((t=getcwd(NULL,MAXNAMLEN))==NULL)
	ShowError(argv[0]);

      if ( (FileNameOut = (char *)malloc( strlen(t) + 1 +
				   strlen(basename(FileNameIn)) + 1))
	  == NULL) 
	ShowError(argv[0]);
      
      if ( *(t+strlen(t)-1)!=':' )
	sprintf(FileNameOut,"%s/%s",t,basename(FileNameIn));
      else
	sprintf(FileNameOut,"%s%s",t,basename(FileNameIn));
      
/*      if ((FileNameOut=(char*)strdup(basename(FileNameIn)))==NULL)
	ShowError(argv[0]);
*/
    }
  else
    {
      char t;
      char *NewFileNameOut;
      
      t = *(FileNameOut+strlen(FileNameOut)-1);	/* The last character */
						/* of FileNameOut. */
      
      if (t==':' || t=='/')	/* The last argument is the name of */
				/* the destination directory. */
	{
	  int NewSize;
	  
	  NewSize = strlen(FileNameOut) + strlen(basename(FileNameIn)) +
	    1 ; 
	  
	  if ((NewFileNameOut= (char *)malloc(NewSize)) == NULL) 
	    ShowError(argv[0]);
	  sprintf(NewFileNameOut,"%s%s",FileNameOut,basename(FileNameIn));
	  free(FileNameOut);
	  FileNameOut = NewFileNameOut;
	}					      
    }
  
  if (FileNameIn==NULL | Size==0)
    usage(argv[0]);

  if ((In=open(FileNameIn,O_RDONLY|O_BINARY))<0)
    ShowError(argv[0]);

  if (stat(FileNameIn,&StatBuffer)==0)
    {
      long OriginalSize;
      char t[256];
      
      OriginalSize= StatBuffer.st_size;
      NumberMaxOfFile = FileNumberBase + (OriginalSize/Size) + (OriginalSize%Size == 0
					       ? 0 : 1);
      sprintf(t,"%d",NumberMaxOfFile);
      if ((StringTemplate=(char *)malloc(strlen("%0d")+strlen(t)+1))==NULL)
	ShowError(argv[0]);
      sprintf(StringTemplate,"%%s%%0%dd",strlen(t));      
    }
  else
    ShowError(argv[0]);
  
  if ((Buffer=(char*)malloc(sizeof(char)*BufferSize))==NULL)
    ShowError(argv[0]);
  
  for(FileNumber=FileNumberBase;FileNumber<NumberMaxOfFile ;FileNumber++)
    {
      Out=OpenOutputFile(FileNameOut,FileNumber,StringTemplate);
      
      for(i=1;(i<=(int)(Size/BufferSize)+((Size % BufferSize) > 1 ? 1
					  : 0)) ;i++) 
	{
	  NumberOfCharToRead=(int)(Size/(BufferSize*i)) >=1 ?
	    BufferSize : Size % BufferSize;
	  
	  if ((NumberOfCharRead=read(In,Buffer,NumberOfCharToRead))!=NumberOfCharToRead)
	    {
	      if (NumberOfCharRead<0)
		ShowError(argv[0]);
	    }

	  if (write(Out,Buffer,NumberOfCharRead)!=NumberOfCharRead)
	    ShowError(argv[0]);
	}
      close(Out);
    }
  
  close(In);
  return 0;

  
}
