/******************************************************************************/
/*                                                                            */
/*                        RAINE FILE ACCESS/ZIP SUPPORT                       */
/*                                                                            */
/******************************************************************************/

#include <stdio.h>
#include <ctype.h>
#include <string.h>
#include <sys/stat.h> // mkdir
#include "raine.h"
#include "unzip.h"
#include "files.h"
#include "starhelp.h"
#include "version.h" // To recompile when the makefile changes (RAINE_DEBUG)

#ifdef __MINGW32__
/* Strange that mingw does not define the standard posix mkdir... windows even has
   file permissons now, even if it's messy */
#define my_mkdir(name) mkdir(name)
#else
#define my_mkdir(name) mkdir(name, 0700)
#endif

static char shared[256];

char *get_shared(char *name) {
#ifdef RAINE_UNIX
  /* Start by looking in the personnal dir (exe_path) */
  FILE *f;
  sprintf(shared, "%s%s", dir_cfg.exe_path,name);
  f=fopen(shared,"rb");
  if (f) {
    fclose(f);
    print_debug("get_shared: using personnal %s\n",shared);
    return shared;
  }
#endif
  sprintf(shared, "%s%s", dir_cfg.share_path,name);
  // don't even check if it exists because we can't do anything about it !
  print_debug("get_shared: using default %s\n",shared);
  return shared;
}

void mkdir_rwx(char *name) {
  char str[256];
  // If path is not absolute (relative then)
  if
#ifndef RAINE_UNIX
  (name[1] != ':' && name[0] != *SLASH)
#else
  (name[0] != *SLASH)
#endif
  {
    sprintf(str,"%s%s",dir_cfg.exe_path,name);
    my_mkdir(str);
  } else { // absolute path, just do it
    my_mkdir(name);
  }
}

int load_file(char *filename, UINT8 *dest, UINT32 size)
{
   FILE *file_ptr;

   file_ptr = fopen(filename,"rb");

   if(file_ptr){
      fread(dest, 1, size, file_ptr);
      fclose(file_ptr);
      return 1;		// Success
   }
   else{
      return 0;		// Failure
   }
}

int save_file(char *filename, UINT8 *source, UINT32 size)
{
   FILE *file_ptr;

   file_ptr = fopen(filename,"wb");

   if(file_ptr){
      fwrite(source, 1, size, file_ptr);
      fclose(file_ptr);
      return 1;		// Success
   }
   else{
      return 0;		// Failure
   }
}

int size_file(char *filename)
{
   int len;
   FILE *file_ptr;

   len = 0;

   file_ptr = fopen(filename,"rb");

   if(file_ptr){

      if(!(fseek(file_ptr,0,SEEK_END))){
         len = ftell(file_ptr);
         if(len<0) len=0;
      }

      fclose(file_ptr);
   }

   return len;
}

/*

find a file by filename

*/

int unz_locate_file_name(unzFile file, char *name)
{
	int err;

    	if(!name)
		return UNZ_PARAMERROR;

	err = unzGoToFirstFile(file);

	while (err == UNZ_OK)
	{
		char current[256+1];

		unzGetCurrentFileInfo(file,NULL,current,256,NULL,0,NULL,0);

		if(!unzStringFileNameCompare(current,name,2))
			return UNZ_OK;

		err = unzGoToNextFile(file);
	}

	return err;
}

/*

find a file by crc32

*/

int unz_locate_file_crc32(unzFile file, UINT32 crc32)
{
	int err;

	if (!crc32)
		return UNZ_PARAMERROR;

	err = unzGoToFirstFile(file);

	while (err == UNZ_OK)
	{
		unz_file_info file_info;

		unzGetCurrentFileInfo(file,&file_info,NULL,0,NULL,0,NULL,0);

		if (file_info.crc == crc32 || file_info.crc == ~crc32)
			return UNZ_OK;

		err = unzGoToNextFile(file);
	}

	return err;
}

#ifdef RAINE_DEBUG

void save_debug(char *name, UINT8 *src, UINT32 size, UINT32 mode)
{
   if(debug_mode){
      char str[256];

      if(src){

         if(mode)
            ByteSwap(src,size);

         sprintf(str,"%sdebug/%s", dir_cfg.exe_path, name);
         save_file(str, src, size);

         print_debug("Debug Save: '%s' saved.\n", name);

      }
      else{

         print_debug("Debug Save: '%s' is NULL.\n", name);

      }

   }

}

#endif
