mirror of
				https://github.com/c64scene-ar/llvm-6502.git
				synced 2025-11-04 05:17:07 +00:00 
			
		
		
		
	git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@10744 91177308-0d34-0410-b5e6-96231b3b80d8
		
			
				
	
	
		
			102 lines
		
	
	
		
			3.2 KiB
		
	
	
	
		
			C
		
	
	
	
	
	
			
		
		
	
	
			102 lines
		
	
	
		
			3.2 KiB
		
	
	
	
		
			C
		
	
	
	
	
	
/*===- StorageProxy.c - OS implementation of the caching interface --------===*\
 | 
						|
 *                                                                            *
 | 
						|
 * This file implements the interface that we will expect operating           *
 | 
						|
 * systems to implement if they wish to support offline cachine.              *
 | 
						|
 *                                                                            *
 | 
						|
\*===----------------------------------------------------------------------===*/
 | 
						|
 | 
						|
#include "OSInterface.h"
 | 
						|
#include "SysUtils.h"
 | 
						|
#include "Config/fcntl.h"
 | 
						|
#include "Config/unistd.h"
 | 
						|
#include "Config/sys/types.h"
 | 
						|
#include "Config/sys/stat.h"
 | 
						|
#include <stdlib.h>
 | 
						|
#include <stdio.h>
 | 
						|
#include <string.h>
 | 
						|
 | 
						|
static const char CacheRoot[] = "/tmp/LLVMCache";
 | 
						|
static const char ExeSuffix[] = ".exe";
 | 
						|
 | 
						|
char* computeCachedFile(const char *key) {
 | 
						|
  /* CacheRoot + "/" + std::string(key) + ExeSuffix; */
 | 
						|
  char *cacheFile = (char*) malloc(strlen(CacheRoot) + 1 + strlen(key) + 
 | 
						|
                                   strlen(ExeSuffix) + 1);
 | 
						|
  char *pCacheFile = cacheFile;
 | 
						|
  if (!cacheFile) return 0;
 | 
						|
  memcpy(cacheFile, CacheRoot, strlen(CacheRoot));
 | 
						|
  pCacheFile += strlen(CacheRoot);
 | 
						|
  *pCacheFile++ = '/';
 | 
						|
  memcpy(pCacheFile, key, strlen(key));
 | 
						|
  pCacheFile += strlen(key);
 | 
						|
  memcpy(pCacheFile, ExeSuffix, strlen(ExeSuffix));
 | 
						|
  pCacheFile += strlen(ExeSuffix);
 | 
						|
  *pCacheFile = 0; // Null-terminate
 | 
						|
  return cacheFile;
 | 
						|
}
 | 
						|
 | 
						|
/*
 | 
						|
 * llvmStat - equivalent to stat(3), except the key may not necessarily
 | 
						|
 * correspond to a file by that name, implementation is up to the OS.
 | 
						|
 * Values returned in buf are similar as they are in Unix.
 | 
						|
 */
 | 
						|
void llvmStat(const char *key, struct stat *buf) {
 | 
						|
  char* cacheFile = computeCachedFile(key);
 | 
						|
  fprintf(stderr, "llvmStat(%s)\n", cacheFile);
 | 
						|
  stat(cacheFile, buf);
 | 
						|
  free(cacheFile);
 | 
						|
}
 | 
						|
 | 
						|
/*
 | 
						|
 * llvmWriteFile - implements a 'save' of a file in the OS. 'key' may not
 | 
						|
 * necessarily map to a file of the same name.
 | 
						|
 * Returns:
 | 
						|
 * 0 - success
 | 
						|
 * non-zero - error
 | 
						|
 */ 
 | 
						|
int llvmWriteFile(const char *key, const void *data, size_t len)
 | 
						|
{
 | 
						|
  char* cacheFile = computeCachedFile(key);
 | 
						|
  int fd = open(cacheFile, O_CREAT|O_WRONLY|O_TRUNC);
 | 
						|
  free(cacheFile);
 | 
						|
  if (fd < 0) return -1; // encountered an error
 | 
						|
  if (write(fd, data, len)) return -1;
 | 
						|
  if (fsync(fd)) return -1;
 | 
						|
  if (close(fd)) return -1;
 | 
						|
  return 0;
 | 
						|
}
 | 
						|
 | 
						|
/* 
 | 
						|
 * llvmReadFile - tells the OS to load data corresponding to a particular key
 | 
						|
 * somewhere into memory.
 | 
						|
 * Returns:
 | 
						|
 * 0 - failure
 | 
						|
 * non-zero - address of loaded file
 | 
						|
 *
 | 
						|
 * Value of size is the length of data loaded into memory.
 | 
						|
 */ 
 | 
						|
void* llvmReadFile(const char *key, size_t *size) {
 | 
						|
  char* cacheFile = computeCachedFile(key);
 | 
						|
  if (!cacheFile) return 0;
 | 
						|
  struct stat buf;
 | 
						|
  stat(cacheFile, &buf);
 | 
						|
  int fd = open(cacheFile, O_RDONLY);
 | 
						|
  if (fd < 0) return 0; // encountered an error
 | 
						|
  void* data = malloc(buf.st_size);
 | 
						|
  if (read(fd, data, buf.st_size)) {
 | 
						|
    free(data);  
 | 
						|
    return 0;
 | 
						|
  }
 | 
						|
  *size = buf.st_size;
 | 
						|
  return data;
 | 
						|
}
 | 
						|
 | 
						|
/*
 | 
						|
 * llvmExecve - execute a file from cache. This is a temporary proof-of-concept
 | 
						|
 * because we do not relocate what we can read from disk.
 | 
						|
 */
 | 
						|
int llvmExecve(const char *filename, char *const argv[], char *const envp[]) {
 | 
						|
  char* cacheFile = computeCachedFile(filename);
 | 
						|
  executeProgram(cacheFile, argv, envp);
 | 
						|
}
 |