added extension to temp files
[swftools.git] / lib / os.c
index c8135f6..a4142ff 100755 (executable)
--- a/lib/os.c
+++ b/lib/os.c
@@ -26,14 +26,32 @@ Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA */
 #include <string.h>
 #ifdef WIN32
 #include <windows.h>
+#else
+#include <unistd.h>
+#include <fcntl.h>
+#endif
+#ifdef HAVE_SYS_STAT_H
+#include <sys/stat.h>
+#else
+#undef HAVE_STAT
+#endif
+#ifdef HAVE_SYS_MMAN_H
+#include <sys/mman.h>
+#else
+#undef HAVE_MMAP
+#endif
+#ifdef HAVE_SYS_TYPES_H
+#include <sys/types.h>
+#else
+#undef HAVE_STAT
 #endif
 
 #if defined(CYGWIN)
-static char seperator = '/';
+char path_seperator = '/';
 #elif defined(WIN32)
-static char seperator = '\\';
+char path_seperator = '\\';
 #else
-static char seperator = '/';
+char path_seperator = '/';
 #endif
 
 #ifdef WIN32
@@ -45,19 +63,26 @@ char* getRegistryEntry(char*path)
     long size = 0;
     DWORD type;
     char*buf;
-    rc = RegOpenKeyEx(HKEY_LOCAL_MACHINE, path, 0, KEY_ALL_ACCESS/* KEY_READ*/, &key);
-    if (rc != ERROR_SUCCESS) {
+    rc = RegOpenKeyEx(HKEY_CURRENT_USER, path, 0, KEY_ALL_ACCESS, &key);
+    if(rc)
+       rc = RegOpenKeyEx(HKEY_CURRENT_USER, path, 0, KEY_READ, &key);
+    if(rc)
+       rc = RegOpenKeyEx(HKEY_LOCAL_MACHINE, path, 0, KEY_ALL_ACCESS, &key);
+    if(rc)
+       rc = RegOpenKeyEx(HKEY_LOCAL_MACHINE, path, 0, KEY_READ, &key);
+
+    if (rc) {
        fprintf(stderr, "RegOpenKeyEx failed\n");
        return 0;
     }
-    rc = RegQueryValueEx(key, NULL, 0, 0, 0, &size) ;
-    if(rc != ERROR_SUCCESS) {
+    rc = RegQueryValueEx(key, NULL, 0, 0, 0, (LPDWORD)&size) ;
+    if(rc) {
        fprintf(stderr, "RegQueryValueEx(1) failed: %d\n", rc);
        return 0;
     }
-    buf = malloc(size+1);
-    rc = RegQueryValueEx(key, NULL, 0, &type, (BYTE*)buf, &size);
-    if(rc != ERROR_SUCCESS) {
+    buf = (char*)malloc(size+1);
+    rc = RegQueryValueEx(key, NULL, 0, &type, (BYTE*)buf, (LPDWORD)&size);
+    if(rc) {
        fprintf(stderr, "RegQueryValueEx(2) failed: %d\n", rc);
        return 0;
     }
@@ -70,19 +95,25 @@ char* getRegistryEntry(char*path)
     } else if(type == REG_BINARY) {
        return buf;
     }
+    return 0;
 }
 
 int setRegistryEntry(char*key,char*value)
 {
-    HKEY hkey;
-    int ret = 0;
-    ret = RegCreateKey(HKEY_LOCAL_MACHINE, key, &hkey);
-    if(ret != ERROR_SUCCESS) {
+    HKEY hkey1;
+    HKEY hkey2;
+    int ret1 = 0, ret2=0;
+    ret1 = RegCreateKey(HKEY_CURRENT_USER, key, &hkey1);
+    ret2 = RegCreateKey(HKEY_LOCAL_MACHINE, key, &hkey2);
+    if(ret1 && ret2) {
        fprintf(stderr, "registry: CreateKey %s failed\n", key);
        return 0;
     }
-    ret = RegSetValue(hkey, NULL, REG_SZ, value, strlen(value)+1);
-    if(ret != ERROR_SUCCESS) {
+    if(!ret1)
+       ret1 = RegSetValue(hkey1, NULL, REG_SZ, value, strlen(value)+1);
+    if(!ret2)
+       ret2 = RegSetValue(hkey2, NULL, REG_SZ, value, strlen(value)+1);
+    if(ret1 && ret2) {
        fprintf(stderr, "registry: SetValue %s failed\n", key);
        return 0;
     }
@@ -109,29 +140,29 @@ char* getInstallationPath()
 #endif
 }
 
-char* concatPaths(char*base, char*add)
+char* concatPaths(const char*base, const char*add)
 {
     int l1 = strlen(base);
     int l2 = strlen(add);
     int pos = 0;
     char*n = 0;
-    while(l1 && base[l1-1] == seperator)
+    while(l1 && base[l1-1] == path_seperator)
        l1--;
-    while(pos < l2 && add[pos] == seperator)
+    while(pos < l2 && add[pos] == path_seperator)
        pos++;
 
-    n = malloc(l1 + (l2-pos) + 2);
+    n = (char*)malloc(l1 + (l2-pos) + 2);
     memcpy(n,base,l1);
-    n[l1]=seperator;
+    n[l1]=path_seperator;
     strcpy(&n[l1+1],&add[pos]);
     return n;
 }
 
-char* stripFilename(char*filename, char*newext)
+char* stripFilename(const char*filename, const char*newext)
 {
     char*last1 = strrchr(filename, '/');
     char*last2 = strrchr(filename, '\\');
-    char*pos = filename;
+    const char*pos = filename;
     char*name;
     char*dot;
     if(last1>pos) pos = last1 + 1;
@@ -147,3 +178,133 @@ char* stripFilename(char*filename, char*newext)
     return name;
 }
 
+static char* getTempDir()
+{
+#ifdef WIN32
+    char*dir = getenv("TMP");
+    if(!dir) dir = getenv("TEMP");
+    if(!dir) dir = getenv("tmp");
+    if(!dir) dir = getenv("temp");
+    if(!dir) dir = "C:\\";
+#else
+    char* dir = "/tmp/";
+#endif
+    return dir;
+}
+
+char* mktempname(char*ptr, const char*ext) {
+    static char tmpbuf[160];
+    char*dir = getTempDir();
+    int l = strlen(dir);
+    char*sep = "";
+    if(!ptr)
+       ptr = tmpbuf;
+    if(l && dir[l-1]!='/' && dir[l-1]!='\\') {
+#ifdef WIN32
+       sep = "\\";
+#else
+       sep = "/";
+#endif
+    }
+
+#ifdef HAVE_LRAND48
+    unsigned int r1 = (unsigned int)lrand48();
+    unsigned int r2 = (unsigned int)lrand48();
+#elif HAVE_RAND
+    unsigned int r1 = rand();
+    unsigned int r2 = rand();
+#else
+    static int count = 1;
+    unsigned int r1 = time(0);
+    unsigned int r2 = (unsigned int)tmpbuf<<8^count;
+    count ++;
+#endif
+    if(ext) {
+       sprintf(ptr, "%s%s%04x%04x.%s",dir,sep,r1,r2,ext);
+    } else {
+       sprintf(ptr, "%s%s%04x%04x",dir,sep,r1,r2);
+    }
+    return ptr;
+}
+
+memfile_t* memfile_open(const char*path)
+{
+    memfile_t*file = malloc(sizeof(memfile_t));
+#if defined(HAVE_MMAP) && defined(HAVE_STAT)
+    int fi = open(path, O_RDONLY);
+    if(fi<0) {
+        perror(path);
+        free(file);
+        return 0;
+    }
+    struct stat sb;
+    if(fstat(fi, &sb)<0) {
+        perror(path);
+        return 0;
+    }
+    file->len = sb.st_size;
+    file->data = mmap(0, sb.st_size, PROT_READ, MAP_PRIVATE, fi, 0);
+#else
+    FILE*fi = fopen(path, "rb");
+    if(!fi) {
+        perror(path);
+        free(file);
+        return 0;
+    }
+    fseek(fi, 0, SEEK_END);
+    file->len = ftell(fi);
+    fseek(fi, 0, SEEK_SET);
+    file->data = malloc(file->len);
+    if(!file->data) {
+        fprintf(stderr, "Out of memory while allocating memory for file %s\n", path);
+        free(file);
+        return 0;
+    }
+    fread(file->data, file->len, 1, fi);
+    fclose(fi);
+#endif
+    return file;
+}
+
+void memfile_close(memfile_t*file)
+{
+#if defined(HAVE_MMAP) && defined(HAVE_STAT)
+    munmap(file->data, file->len);
+#else
+    free(file->data);
+#endif
+    file->data = 0;
+    file->len = 0;
+    free(file);
+}
+
+void move_file(const char*from, const char*to)
+{
+    int result = rename(from, to);
+
+    if(result==0) return; //done!
+
+    /* if we can't rename, for some reason, copy the file
+       manually */
+    FILE*fi = fopen(from, "rb");
+    if(!fi) {
+       perror(from);
+       return;
+    }
+    FILE*fo = fopen(to, "wb");
+    if(!fo) {
+       perror(to);
+       return;
+    }
+    char buffer[16384];
+    while(1) {
+       int bytes = fread(buffer, 16384, 1, fi);
+       if(bytes<=0)
+           return;
+       fwrite(buffer, bytes, 1, fo);
+    }
+
+    fclose(fo);
+    fclose(fi);
+}
+