mirror of
https://github.com/QB64-Phoenix-Edition/QB64pe.git
synced 2024-07-06 19:50:22 +00:00
Consolidate all filesystem related functions to it's own translation unit
This commit is contained in:
parent
79d48113f2
commit
0e251eb8e8
|
@ -21,6 +21,8 @@
|
|||
#include "compression.h"
|
||||
#include "datetime.h"
|
||||
#include "event.h"
|
||||
#include "filepath.h"
|
||||
#include "filesystem.h"
|
||||
#include "font.h"
|
||||
#include "game_controller.h"
|
||||
#include "glut-thread.h"
|
||||
|
@ -3946,23 +3948,6 @@ int32 exit_value = 0;
|
|||
|
||||
void error(int32 error_number); // for forward references
|
||||
|
||||
char *fixdir(qbs *filename) {
|
||||
// note: changes the slashes in a filename to make it compatible with the OS
|
||||
// applied to QB commands: open, bload/bsave, loadfont, loadimage, sndopen/sndplayfile
|
||||
static int32 i;
|
||||
|
||||
for (i = 0; i < filename->len; i++) {
|
||||
#ifdef QB64_WINDOWS
|
||||
if (filename->chr[i] == 47)
|
||||
filename->chr[i] = 92;
|
||||
#else
|
||||
if (filename->chr[i] == 92)
|
||||
filename->chr[i] = 47;
|
||||
#endif
|
||||
}
|
||||
return (char *)filename->chr;
|
||||
}
|
||||
|
||||
int32 width8050switch = 1; // if set, can automatically switch to WIDTH 80,50 if LOCATE'ing beyond row 26
|
||||
|
||||
uint32 pal[256];
|
||||
|
@ -23022,166 +23007,6 @@ shell_complete:;
|
|||
|
||||
} //_DONTWAIT & _HIDE
|
||||
|
||||
void sub_kill(qbs *str) {
|
||||
// note: file not found returned for non-existant paths too
|
||||
// file already open returned if access unavailable
|
||||
if (new_error)
|
||||
return;
|
||||
static int32 i;
|
||||
static qbs *strz = NULL;
|
||||
if (!strz)
|
||||
strz = qbs_new(0, 0);
|
||||
qbs_set(strz, qbs_add(str, qbs_new_txt_len("\0", 1)));
|
||||
#ifdef QB64_WINDOWS
|
||||
static WIN32_FIND_DATA fd;
|
||||
static HANDLE hFind;
|
||||
static qbs *strpath = NULL;
|
||||
if (!strpath)
|
||||
strpath = qbs_new(0, 0);
|
||||
static qbs *strfullz = NULL;
|
||||
if (!strfullz)
|
||||
strfullz = qbs_new(0, 0);
|
||||
// find path
|
||||
qbs_set(strpath, strz);
|
||||
for (i = strpath->len; i > 0; i--) {
|
||||
if ((strpath->chr[i - 1] == 47) || (strpath->chr[i - 1] == 92)) {
|
||||
strpath->len = i;
|
||||
break;
|
||||
}
|
||||
} // i
|
||||
if (i == 0)
|
||||
strpath->len = 0; // no path specified
|
||||
static int32 count;
|
||||
count = 0;
|
||||
hFind = FindFirstFile(fixdir(strz), &fd);
|
||||
if (hFind == INVALID_HANDLE_VALUE) {
|
||||
error(53);
|
||||
return;
|
||||
} // file not found
|
||||
do {
|
||||
if ((fd.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) == 0) {
|
||||
qbs_set(strfullz, qbs_add(strpath, qbs_new_txt_len(fd.cFileName, strlen(fd.cFileName) + 1)));
|
||||
if (!DeleteFile((char *)strfullz->chr)) {
|
||||
i = GetLastError();
|
||||
if ((i == 5) || (i == 19) || (i == 33) || (i == 32)) {
|
||||
FindClose(hFind);
|
||||
error(55);
|
||||
return;
|
||||
} // file already open
|
||||
FindClose(hFind);
|
||||
error(53);
|
||||
return; // file not found
|
||||
}
|
||||
count++;
|
||||
} // not a directory
|
||||
} while (FindNextFile(hFind, &fd));
|
||||
FindClose(hFind);
|
||||
if (!count) {
|
||||
error(53);
|
||||
return;
|
||||
} // file not found
|
||||
return;
|
||||
#else
|
||||
if (remove(fixdir(strz))) {
|
||||
i = errno;
|
||||
if (i == ENOENT) {
|
||||
error(53);
|
||||
return;
|
||||
} // file not found
|
||||
if (i == EACCES) {
|
||||
error(75);
|
||||
return;
|
||||
} // path/file access error
|
||||
error(64); // bad file name (assumed)
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
void sub_name(qbs *oldname, qbs *newname) {
|
||||
if (new_error)
|
||||
return;
|
||||
static qbs *strz = NULL;
|
||||
if (!strz)
|
||||
strz = qbs_new(0, 0);
|
||||
static qbs *strz2 = NULL;
|
||||
if (!strz2)
|
||||
strz2 = qbs_new(0, 0);
|
||||
static int32 i;
|
||||
qbs_set(strz, qbs_add(oldname, qbs_new_txt_len("\0", 1)));
|
||||
qbs_set(strz2, qbs_add(newname, qbs_new_txt_len("\0", 1)));
|
||||
if (rename(fixdir(strz), fixdir(strz2))) {
|
||||
i = errno;
|
||||
if (i == ENOENT) {
|
||||
error(53);
|
||||
return;
|
||||
} // file not found
|
||||
if (i == EINVAL) {
|
||||
error(64);
|
||||
return;
|
||||
} // bad file name
|
||||
if (i == EACCES) {
|
||||
error(75);
|
||||
return;
|
||||
} // path/file access error
|
||||
error(5); // Illegal function call (assumed)
|
||||
}
|
||||
}
|
||||
|
||||
void sub_chdir(qbs *str) {
|
||||
|
||||
if (new_error)
|
||||
return;
|
||||
static qbs *strz = NULL;
|
||||
if (!strz)
|
||||
strz = qbs_new(0, 0);
|
||||
qbs_set(strz, qbs_add(str, qbs_new_txt_len("\0", 1)));
|
||||
if (chdir(fixdir(strz)) == -1) {
|
||||
// assume errno==ENOENT
|
||||
error(76); // path not found
|
||||
}
|
||||
|
||||
static int32 tmp_long;
|
||||
static int32 got_ports = 0;
|
||||
}
|
||||
|
||||
void sub_mkdir(qbs *str) {
|
||||
if (new_error)
|
||||
return;
|
||||
static qbs *strz = NULL;
|
||||
if (!strz)
|
||||
strz = qbs_new(0, 0);
|
||||
qbs_set(strz, qbs_add(str, qbs_new_txt_len("\0", 1)));
|
||||
#ifdef QB64_UNIX
|
||||
if (mkdir(fixdir(strz), 0770) == -1) {
|
||||
#else
|
||||
if (mkdir(fixdir(strz)) == -1) {
|
||||
#endif
|
||||
if (errno == EEXIST) {
|
||||
error(75);
|
||||
return;
|
||||
} // path/file access error
|
||||
// assume errno==ENOENT
|
||||
error(76); // path not found
|
||||
}
|
||||
}
|
||||
|
||||
void sub_rmdir(qbs *str) {
|
||||
if (new_error)
|
||||
return;
|
||||
static qbs *strz = NULL;
|
||||
if (!strz)
|
||||
strz = qbs_new(0, 0);
|
||||
qbs_set(strz, qbs_add(str, qbs_new_txt_len("\0", 1)));
|
||||
if (rmdir(fixdir(strz)) == -1) {
|
||||
if (errno == ENOTEMPTY) {
|
||||
error(75);
|
||||
return;
|
||||
} // path/file access error
|
||||
// assume errno==ENOENT
|
||||
error(76); // path not found
|
||||
}
|
||||
}
|
||||
|
||||
long double pow2(long double x, long double y) {
|
||||
if (x < 0) {
|
||||
if (y != std::floor(y)) {
|
||||
|
@ -31669,134 +31494,6 @@ failed:;
|
|||
|
||||
#endif
|
||||
|
||||
void sub_files(qbs *str, int32 passed) {
|
||||
if (new_error)
|
||||
return;
|
||||
|
||||
static int32 i, i2, i3;
|
||||
static qbs *strz = NULL;
|
||||
if (!strz)
|
||||
strz = qbs_new(0, 0);
|
||||
|
||||
if (passed) {
|
||||
qbs_set(strz, qbs_add(str, qbs_new_txt_len("\0", 1)));
|
||||
} else {
|
||||
qbs_set(strz, qbs_new_txt_len("\0", 1));
|
||||
}
|
||||
|
||||
#ifdef QB64_WINDOWS
|
||||
static WIN32_FIND_DATA fd;
|
||||
static HANDLE hFind;
|
||||
static qbs *strpath = NULL;
|
||||
if (!strpath)
|
||||
strpath = qbs_new(0, 0);
|
||||
static qbs *strz2 = NULL;
|
||||
if (!strz2)
|
||||
strz2 = qbs_new(0, 0);
|
||||
|
||||
i = 0;
|
||||
if (strz->len >= 2) {
|
||||
if (strz->chr[strz->len - 2] == 92)
|
||||
i = 1;
|
||||
} else
|
||||
i = 1;
|
||||
if (i) { // add * (and new NULL term.)
|
||||
strz->chr[strz->len - 1] = 42; //"*"
|
||||
qbs_set(strz, qbs_add(strz, qbs_new_txt_len("\0", 1)));
|
||||
}
|
||||
|
||||
qbs_set(strpath, strz);
|
||||
|
||||
for (i = strpath->len; i > 0; i--) {
|
||||
if ((strpath->chr[i - 1] == 47) || (strpath->chr[i - 1] == 92)) {
|
||||
strpath->len = i;
|
||||
break;
|
||||
}
|
||||
} // i
|
||||
if (i == 0)
|
||||
strpath->len = 0; // no path specified
|
||||
|
||||
// print the current path
|
||||
// note: for QBASIC compatibility reasons it does not print the directory name of the files being displayed
|
||||
static uint8 curdir[4096];
|
||||
static uint8 curdir2[4096];
|
||||
i2 = GetCurrentDirectory(4096, (char *)curdir);
|
||||
if (i2) {
|
||||
i2 = GetShortPathName((char *)curdir, (char *)curdir2, 4096);
|
||||
if (i2) {
|
||||
qbs_set(strz2, qbs_ucase(qbs_new_txt_len((char *)curdir2, i2)));
|
||||
qbs_print(strz2, 1);
|
||||
} else {
|
||||
error(5);
|
||||
return;
|
||||
}
|
||||
} else {
|
||||
error(5);
|
||||
return;
|
||||
}
|
||||
|
||||
hFind = FindFirstFile(fixdir(strz), &fd);
|
||||
if (hFind == INVALID_HANDLE_VALUE) {
|
||||
error(53);
|
||||
return;
|
||||
} // file not found
|
||||
do {
|
||||
|
||||
if (!fd.cAlternateFileName[0]) { // no alternate filename exists
|
||||
qbs_set(strz2, qbs_ucase(qbs_new_txt_len(fd.cFileName, strlen(fd.cFileName))));
|
||||
} else {
|
||||
qbs_set(strz2, qbs_ucase(qbs_new_txt_len(fd.cAlternateFileName, strlen(fd.cAlternateFileName))));
|
||||
}
|
||||
|
||||
if (strz2->len < 12) { // padding required
|
||||
qbs_set(strz2, qbs_add(strz2, func_space(12 - strz2->len)));
|
||||
i2 = 0;
|
||||
for (i = 0; i < 12; i++) {
|
||||
if (strz2->chr[i] == 46) {
|
||||
memmove(&strz2->chr[8], &strz2->chr[i], 4);
|
||||
memset(&strz2->chr[i], 32, 8 - i);
|
||||
break;
|
||||
}
|
||||
} // i
|
||||
} // padding
|
||||
|
||||
// add " " or "<DIR> "
|
||||
if (fd.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) {
|
||||
qbs_set(strz2, qbs_add(strz2, qbs_new_txt_len("<DIR> ", 6)));
|
||||
} else {
|
||||
qbs_set(strz2, qbs_add(strz2, func_space(6)));
|
||||
}
|
||||
|
||||
makefit(strz2);
|
||||
qbs_print(strz2, 0);
|
||||
|
||||
} while (FindNextFile(hFind, &fd));
|
||||
FindClose(hFind);
|
||||
|
||||
static ULARGE_INTEGER FreeBytesAvailableToCaller;
|
||||
static ULARGE_INTEGER TotalNumberOfBytes;
|
||||
static ULARGE_INTEGER TotalNumberOfFreeBytes;
|
||||
static int64 bytes;
|
||||
static char *cp;
|
||||
qbs_set(strpath, qbs_add(strpath, qbs_new_txt_len("\0", 1)));
|
||||
cp = (char *)strpath->chr;
|
||||
if (strpath->len == 1)
|
||||
cp = NULL;
|
||||
if (GetDiskFreeSpaceEx(cp, &FreeBytesAvailableToCaller, &TotalNumberOfBytes, &TotalNumberOfFreeBytes)) {
|
||||
bytes = *(int64 *)(void *)&FreeBytesAvailableToCaller;
|
||||
} else {
|
||||
bytes = 0;
|
||||
}
|
||||
if (func_pos(NULL) > 1) {
|
||||
strz2->len = 0;
|
||||
qbs_print(strz2, 1);
|
||||
} // new line if necessary
|
||||
qbs_set(strz2, qbs_add(qbs_str(bytes), qbs_new_txt_len(" Bytes free", 11)));
|
||||
qbs_print(strz2, 1);
|
||||
|
||||
#endif
|
||||
}
|
||||
|
||||
int32 func__keyhit() {
|
||||
/*
|
||||
//keyhit cyclic buffer
|
||||
|
@ -33463,65 +33160,6 @@ int32 func_strig(int32 i, int32 controller, int32 passed) {
|
|||
return 0;
|
||||
}
|
||||
|
||||
int32 func__fileexists(qbs *file) {
|
||||
if (new_error)
|
||||
return 0;
|
||||
static qbs *strz = NULL;
|
||||
if (!strz)
|
||||
strz = qbs_new(0, 0);
|
||||
qbs_set(strz, qbs_add(file, qbs_new_txt_len("\0", 1)));
|
||||
#ifdef QB64_WINDOWS
|
||||
static int32 x;
|
||||
x = GetFileAttributes(fixdir(strz));
|
||||
if (x == INVALID_FILE_ATTRIBUTES)
|
||||
return 0;
|
||||
if (x & FILE_ATTRIBUTE_DIRECTORY)
|
||||
return 0;
|
||||
return -1;
|
||||
#elif defined(QB64_UNIX)
|
||||
struct stat sb;
|
||||
if (stat(fixdir(strz), &sb) == 0 && S_ISREG(sb.st_mode))
|
||||
return -1;
|
||||
return 0;
|
||||
#else
|
||||
// generic method (not currently used)
|
||||
static std::ifstream fh;
|
||||
fh.open(fixdir(strz), std::ios::binary | std::ios::in);
|
||||
if (fh.is_open() == NULL) {
|
||||
fh.clear(std::ios::goodbit);
|
||||
return 0;
|
||||
}
|
||||
fh.clear(std::ios::goodbit);
|
||||
fh.close();
|
||||
return -1;
|
||||
#endif
|
||||
}
|
||||
|
||||
int32 func__direxists(qbs *file) {
|
||||
if (new_error)
|
||||
return 0;
|
||||
static qbs *strz = NULL;
|
||||
if (!strz)
|
||||
strz = qbs_new(0, 0);
|
||||
qbs_set(strz, qbs_add(file, qbs_new_txt_len("\0", 1)));
|
||||
#ifdef QB64_WINDOWS
|
||||
static int32 x;
|
||||
x = GetFileAttributes(fixdir(strz));
|
||||
if (x == INVALID_FILE_ATTRIBUTES)
|
||||
return 0;
|
||||
if (x & FILE_ATTRIBUTE_DIRECTORY)
|
||||
return -1;
|
||||
return 0;
|
||||
#elif defined(QB64_UNIX)
|
||||
struct stat sb;
|
||||
if (stat(fixdir(strz), &sb) == 0 && S_ISDIR(sb.st_mode))
|
||||
return -1;
|
||||
return 0;
|
||||
#else
|
||||
return 0; // default response
|
||||
#endif
|
||||
}
|
||||
|
||||
int32 func__console() {
|
||||
if (new_error)
|
||||
return -1;
|
||||
|
@ -36318,219 +35956,8 @@ int32 func__resizeheight() { return resize_event_y; }
|
|||
int32 func__scaledwidth() { return environment_2d__screen_scaled_width; }
|
||||
int32 func__scaledheight() { return environment_2d__screen_scaled_height; }
|
||||
|
||||
// Get Current Working Directory
|
||||
qbs *func__cwd() {
|
||||
qbs *final, *tqbs;
|
||||
int length;
|
||||
char *buf, *ret;
|
||||
|
||||
#if defined QB64_WINDOWS
|
||||
length = GetCurrentDirectoryA(0, NULL);
|
||||
buf = (char *)malloc(length);
|
||||
if (!buf) {
|
||||
error(7); //"Out of memory"
|
||||
return tqbs;
|
||||
}
|
||||
if (GetCurrentDirectoryA(length, buf) != --length) { // Sanity check
|
||||
free(buf); // It's good practice
|
||||
tqbs = qbs_new(0, 1);
|
||||
error(51); //"Internal error"
|
||||
return tqbs;
|
||||
}
|
||||
#elif defined QB64_UNIX
|
||||
length = 512;
|
||||
while (1) {
|
||||
buf = (char *)malloc(length);
|
||||
if (!buf) {
|
||||
tqbs = qbs_new(0, 1);
|
||||
error(7);
|
||||
return tqbs;
|
||||
}
|
||||
ret = getcwd(buf, length);
|
||||
if (ret)
|
||||
break;
|
||||
if (errno != ERANGE) {
|
||||
tqbs = qbs_new(0, 1);
|
||||
error(51);
|
||||
return tqbs;
|
||||
}
|
||||
free(buf);
|
||||
length += 512;
|
||||
}
|
||||
length = strlen(ret);
|
||||
ret = (char *)realloc(ret, length); // Chops off the null byte
|
||||
if (!ret) {
|
||||
tqbs = qbs_new(0, 1);
|
||||
error(7);
|
||||
return tqbs;
|
||||
}
|
||||
buf = ret;
|
||||
#endif
|
||||
final = qbs_new(length, 1);
|
||||
memcpy(final->chr, buf, length);
|
||||
free(buf);
|
||||
return final;
|
||||
}
|
||||
|
||||
qbs *startDir = NULL; // set on startup
|
||||
qbs *func__startdir() {
|
||||
qbs *temp = qbs_new(0, 1);
|
||||
qbs_set(temp, startDir);
|
||||
return temp;
|
||||
}
|
||||
|
||||
qbs *rootDir = NULL; // the dir moved to when program begins
|
||||
|
||||
qbs *func__dir(qbs *context_in) {
|
||||
|
||||
static qbs *context = NULL;
|
||||
if (!context) {
|
||||
context = qbs_new(0, 0);
|
||||
}
|
||||
|
||||
qbs_set(context, qbs_ucase(context_in));
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("TEXT")) || qbs_equal(qbs_ucase(context), qbs_new_txt("DOCUMENT")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("DOCUMENTS")) || qbs_equal(qbs_ucase(context), qbs_new_txt("MY DOCUMENTS"))) {
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 5, NULL, 0, osPath))) { // Documents
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("MUSIC")) || qbs_equal(qbs_ucase(context), qbs_new_txt("AUDIO")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("SOUND")) || qbs_equal(qbs_ucase(context), qbs_new_txt("SOUNDS")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("MY MUSIC"))) {
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 13, NULL, 0, osPath))) { // Music
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("PICTURE")) || qbs_equal(qbs_ucase(context), qbs_new_txt("PICTURES")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("IMAGE")) || qbs_equal(qbs_ucase(context), qbs_new_txt("IMAGES")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("MY PICTURES"))) {
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 39, NULL, 0, osPath))) { // Pictures
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("DCIM")) || qbs_equal(qbs_ucase(context), qbs_new_txt("CAMERA")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("CAMERA ROLL")) || qbs_equal(qbs_ucase(context), qbs_new_txt("PHOTO")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("PHOTOS"))) {
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 39, NULL, 0, osPath))) { // Pictures
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("MOVIE")) || qbs_equal(qbs_ucase(context), qbs_new_txt("MOVIES")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("VIDEO")) || qbs_equal(qbs_ucase(context), qbs_new_txt("VIDEOS")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("MY VIDEOS"))) {
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 14, NULL, 0, osPath))) { // Videos
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("DOWNLOAD")) || qbs_equal(qbs_ucase(context), qbs_new_txt("DOWNLOADS"))) {
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 0x0028, NULL, 0, osPath))) { // user folder
|
||||
// XP & SHGetFolderPathA do not support the concept of a Downloads folder, however it can be constructed
|
||||
mkdir((char *)((qbs_add(qbs_new_txt(osPath), qbs_new_txt_len("\\Downloads\0", 11)))->chr));
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\Downloads\\"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("DESKTOP"))) {
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 0, NULL, 0, osPath))) { // Desktop
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("APPDATA")) || qbs_equal(qbs_ucase(context), qbs_new_txt("APPLICATION DATA")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("PROGRAM DATA")) || qbs_equal(qbs_ucase(context), qbs_new_txt("DATA"))) {
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 0x001a, NULL, 0, osPath))) { // CSIDL_APPDATA (%APPDATA%)
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("LOCALAPPDATA")) || qbs_equal(qbs_ucase(context), qbs_new_txt("LOCAL APPLICATION DATA")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("LOCAL PROGRAM DATA")) || qbs_equal(qbs_ucase(context), qbs_new_txt("LOCAL DATA"))) {
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 0x001c, NULL, 0, osPath))) { // CSIDL_LOCAL_APPDATA (%LOCALAPPDATA%)
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("PROGRAMFILES")) || qbs_equal(qbs_ucase(context), qbs_new_txt("PROGRAM FILES"))) {
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 0x0026, NULL, 0, osPath))) { // CSIDL_PROGRAM_FILES (%PROGRAMFILES%)
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("PROGRAMFILESX86")) || qbs_equal(qbs_ucase(context), qbs_new_txt("PROGRAMFILES X86")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("PROGRAM FILES X86")) || qbs_equal(qbs_ucase(context), qbs_new_txt("PROGRAM FILES 86")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("PROGRAM FILES (X86)")) || qbs_equal(qbs_ucase(context), qbs_new_txt("PROGRAMFILES (X86)")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("PROGRAM FILES(X86)"))) {
|
||||
#ifdef QB64_WINDOWS &&_WIN64
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 0x002a, NULL, 0, osPath))) { // CSIDL_PROGRAM_FILES (%PROGRAMFILES(X86)%)
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("TEMP")) || qbs_equal(qbs_ucase(context), qbs_new_txt("TEMP FILES"))) {
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH + 1];
|
||||
DWORD pathlen;
|
||||
pathlen = GetTempPathA(261, osPath); //%TEMP%
|
||||
char path[pathlen];
|
||||
memcpy(path, &osPath, pathlen);
|
||||
if (pathlen > 0) {
|
||||
return qbs_new_txt(path);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
// general fallback location
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 0, NULL, 0, osPath))) { // desktop
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\"));
|
||||
}
|
||||
return qbs_new_txt(".\\"); // current location
|
||||
#else
|
||||
return qbs_new_txt("./"); // current location
|
||||
#endif
|
||||
}
|
||||
|
||||
extern void set_dynamic_info();
|
||||
|
||||
int main(int argc, char *argv[]) {
|
||||
|
||||
#if defined(QB64_LINUX) && defined(X11)
|
||||
|
@ -36753,9 +36180,6 @@ int main(int argc, char *argv[]) {
|
|||
}
|
||||
#endif
|
||||
|
||||
rootDir = qbs_new(0, 0);
|
||||
qbs_set(rootDir, func__cwd());
|
||||
|
||||
unknown_opcode_mess = qbs_new(0, 0);
|
||||
qbs_set(unknown_opcode_mess, qbs_new_txt_len("Unknown Opcode ( )\0", 20));
|
||||
|
||||
|
|
|
@ -34,6 +34,20 @@ qbs *qbs_new_txt(const char *);
|
|||
qbs *qbs_new_txt_len(const char *, int32_t);
|
||||
qbs *qbs_add(qbs *, qbs *);
|
||||
qbs *qbs_set(qbs *, qbs *);
|
||||
int32 qbs_equal(qbs *str1, qbs *str2);
|
||||
qbs *func_space(int32 spaces);
|
||||
void makefit(qbs *text);
|
||||
qbs *qbs_str(int64 value);
|
||||
qbs *qbs_str(int32 value);
|
||||
qbs *qbs_str(int16 value);
|
||||
qbs *qbs_str(int8 value);
|
||||
qbs *qbs_str(uint64 value);
|
||||
qbs *qbs_str(uint32 value);
|
||||
qbs *qbs_str(uint16 value);
|
||||
qbs *qbs_str(uint8 value);
|
||||
qbs *qbs_str(float value);
|
||||
qbs *qbs_str(double value);
|
||||
qbs *qbs_str(long double value);
|
||||
void qbg_sub_window(float, float, float, float, int32);
|
||||
extern int32 autodisplay;
|
||||
// GFS forward references
|
||||
|
|
|
@ -2,6 +2,7 @@
|
|||
libqb-objs-y += $(PATH_LIBQB)/src/threading.o
|
||||
libqb-objs-y += $(PATH_LIBQB)/src/buffer.o
|
||||
libqb-objs-y += $(PATH_LIBQB)/src/filepath.o
|
||||
libqb-objs-y += $(PATH_LIBQB)/src/filesystem.o
|
||||
libqb-objs-y += $(PATH_LIBQB)/src/datetime.o
|
||||
libqb-objs-y += $(PATH_LIBQB)/src/rounding.o
|
||||
|
||||
|
|
|
@ -1,6 +1,10 @@
|
|||
#ifndef INCLUDE_LIBQB_FILEPATH_H
|
||||
#define INCLUDE_LIBQB_FILEPATH_H
|
||||
|
||||
#include <string>
|
||||
|
||||
struct qbs;
|
||||
|
||||
// Takes a path + filename, and returns just the filename portion
|
||||
// Returns either NULL or empty string if it has none.
|
||||
const char *filepath_get_filename(const char *path);
|
||||
|
@ -12,4 +16,11 @@ const char *filepath_get_extension(const char *fliename);
|
|||
// Returns true if the path is to a file that matches the provided extension
|
||||
bool filepath_has_extension(const char *path, const char *extension);
|
||||
|
||||
// The following overloaded functions changes the path separators in path based on the OS (path is modified)
|
||||
char *filepath_fix_directory(char *path);
|
||||
char *filepath_fix_directory(std::string &path);
|
||||
char *filepath_fix_directory(qbs *path);
|
||||
|
||||
char *fixdir(qbs *);
|
||||
|
||||
#endif
|
||||
|
|
19
internal/c/libqb/include/filesystem.h
Normal file
19
internal/c/libqb/include/filesystem.h
Normal file
|
@ -0,0 +1,19 @@
|
|||
#pragma once
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
struct qbs;
|
||||
|
||||
extern qbs *startDir;
|
||||
|
||||
qbs *func__cwd();
|
||||
qbs *func__dir(qbs *context);
|
||||
int32_t func__direxists(qbs *);
|
||||
int32_t func__fileexists(qbs *);
|
||||
qbs *func__startdir();
|
||||
void sub_chdir(qbs *str);
|
||||
void sub_files(qbs *str, int32_t passed);
|
||||
void sub_kill(qbs *str);
|
||||
void sub_mkdir(qbs *str);
|
||||
void sub_name(qbs *oldname, qbs *newname);
|
||||
void sub_rmdir(qbs *str);
|
|
@ -5,8 +5,9 @@
|
|||
|
||||
#include <string.h>
|
||||
|
||||
const char *filepath_get_filename(const char *path)
|
||||
{
|
||||
#include "../../libqb.h"
|
||||
|
||||
const char *filepath_get_filename(const char *path) {
|
||||
const char *fileName;
|
||||
|
||||
if (path == NULL) {
|
||||
|
@ -32,8 +33,7 @@ const char *filepath_get_filename(const char *path)
|
|||
return fileName;
|
||||
}
|
||||
|
||||
const char *filepath_get_extension(const char *path)
|
||||
{
|
||||
const char *filepath_get_extension(const char *path) {
|
||||
const char *extension;
|
||||
const char *lastOccurance;
|
||||
|
||||
|
@ -57,8 +57,7 @@ const char *filepath_get_extension(const char *path)
|
|||
return (lastOccurance != NULL) ? lastOccurance : extension;
|
||||
}
|
||||
|
||||
bool filepath_has_extension(const char *path, const char *extension)
|
||||
{
|
||||
bool filepath_has_extension(const char *path, const char *extension) {
|
||||
const char *ext1;
|
||||
const char *ext2;
|
||||
|
||||
|
@ -75,3 +74,18 @@ bool filepath_has_extension(const char *path, const char *extension)
|
|||
return strcasecmp(ext1, ext2) == 0;
|
||||
#endif
|
||||
}
|
||||
|
||||
char *fixdir(qbs *filename) {
|
||||
// note: changes the slashes in a filename to make it compatible with the OS
|
||||
// applied to QB commands: open, bload/bsave, loadfont, loadimage, sndopen/sndplayfile
|
||||
for (auto i = 0; i < filename->len; i++) {
|
||||
#ifdef QB64_WINDOWS
|
||||
if (filename->chr[i] == 47)
|
||||
filename->chr[i] = 92;
|
||||
#else
|
||||
if (filename->chr[i] == 92)
|
||||
filename->chr[i] = 47;
|
||||
#endif
|
||||
}
|
||||
return (char *)filename->chr;
|
||||
}
|
||||
|
|
564
internal/c/libqb/src/filesystem.cpp
Normal file
564
internal/c/libqb/src/filesystem.cpp
Normal file
|
@ -0,0 +1,564 @@
|
|||
#include "libqb-common.h"
|
||||
|
||||
#include "filepath.h"
|
||||
#include "filesystem.h"
|
||||
|
||||
#include "../../libqb.h"
|
||||
|
||||
// Get Current Working Directory
|
||||
qbs *func__cwd() {
|
||||
qbs *final, *tqbs;
|
||||
int length;
|
||||
char *buf, *ret;
|
||||
|
||||
#if defined QB64_WINDOWS
|
||||
length = GetCurrentDirectoryA(0, NULL);
|
||||
buf = (char *)malloc(length);
|
||||
if (!buf) {
|
||||
error(7); //"Out of memory"
|
||||
return tqbs;
|
||||
}
|
||||
if (GetCurrentDirectoryA(length, buf) != --length) { // Sanity check
|
||||
free(buf); // It's good practice
|
||||
tqbs = qbs_new(0, 1);
|
||||
error(51); //"Internal error"
|
||||
return tqbs;
|
||||
}
|
||||
#elif defined QB64_UNIX
|
||||
length = 512;
|
||||
while (1) {
|
||||
buf = (char *)malloc(length);
|
||||
if (!buf) {
|
||||
tqbs = qbs_new(0, 1);
|
||||
error(7);
|
||||
return tqbs;
|
||||
}
|
||||
ret = getcwd(buf, length);
|
||||
if (ret)
|
||||
break;
|
||||
if (errno != ERANGE) {
|
||||
tqbs = qbs_new(0, 1);
|
||||
error(51);
|
||||
return tqbs;
|
||||
}
|
||||
free(buf);
|
||||
length += 512;
|
||||
}
|
||||
length = strlen(ret);
|
||||
ret = (char *)realloc(ret, length); // Chops off the null byte
|
||||
if (!ret) {
|
||||
tqbs = qbs_new(0, 1);
|
||||
error(7);
|
||||
return tqbs;
|
||||
}
|
||||
buf = ret;
|
||||
#endif
|
||||
final = qbs_new(length, 1);
|
||||
memcpy(final->chr, buf, length);
|
||||
free(buf);
|
||||
return final;
|
||||
}
|
||||
|
||||
qbs *func__dir(qbs *context_in) {
|
||||
|
||||
static qbs *context = NULL;
|
||||
if (!context) {
|
||||
context = qbs_new(0, 0);
|
||||
}
|
||||
|
||||
qbs_set(context, qbs_ucase(context_in));
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("TEXT")) || qbs_equal(qbs_ucase(context), qbs_new_txt("DOCUMENT")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("DOCUMENTS")) || qbs_equal(qbs_ucase(context), qbs_new_txt("MY DOCUMENTS"))) {
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 5, NULL, 0, osPath))) { // Documents
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("MUSIC")) || qbs_equal(qbs_ucase(context), qbs_new_txt("AUDIO")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("SOUND")) || qbs_equal(qbs_ucase(context), qbs_new_txt("SOUNDS")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("MY MUSIC"))) {
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 13, NULL, 0, osPath))) { // Music
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("PICTURE")) || qbs_equal(qbs_ucase(context), qbs_new_txt("PICTURES")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("IMAGE")) || qbs_equal(qbs_ucase(context), qbs_new_txt("IMAGES")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("MY PICTURES"))) {
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 39, NULL, 0, osPath))) { // Pictures
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("DCIM")) || qbs_equal(qbs_ucase(context), qbs_new_txt("CAMERA")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("CAMERA ROLL")) || qbs_equal(qbs_ucase(context), qbs_new_txt("PHOTO")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("PHOTOS"))) {
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 39, NULL, 0, osPath))) { // Pictures
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("MOVIE")) || qbs_equal(qbs_ucase(context), qbs_new_txt("MOVIES")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("VIDEO")) || qbs_equal(qbs_ucase(context), qbs_new_txt("VIDEOS")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("MY VIDEOS"))) {
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 14, NULL, 0, osPath))) { // Videos
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("DOWNLOAD")) || qbs_equal(qbs_ucase(context), qbs_new_txt("DOWNLOADS"))) {
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 0x0028, NULL, 0, osPath))) { // user folder
|
||||
// XP & SHGetFolderPathA do not support the concept of a Downloads folder, however it can be constructed
|
||||
mkdir((char *)((qbs_add(qbs_new_txt(osPath), qbs_new_txt_len("\\Downloads\0", 11)))->chr));
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\Downloads\\"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("DESKTOP"))) {
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 0, NULL, 0, osPath))) { // Desktop
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("APPDATA")) || qbs_equal(qbs_ucase(context), qbs_new_txt("APPLICATION DATA")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("PROGRAM DATA")) || qbs_equal(qbs_ucase(context), qbs_new_txt("DATA"))) {
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 0x001a, NULL, 0, osPath))) { // CSIDL_APPDATA (%APPDATA%)
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("LOCALAPPDATA")) || qbs_equal(qbs_ucase(context), qbs_new_txt("LOCAL APPLICATION DATA")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("LOCAL PROGRAM DATA")) || qbs_equal(qbs_ucase(context), qbs_new_txt("LOCAL DATA"))) {
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 0x001c, NULL, 0, osPath))) { // CSIDL_LOCAL_APPDATA (%LOCALAPPDATA%)
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("PROGRAMFILES")) || qbs_equal(qbs_ucase(context), qbs_new_txt("PROGRAM FILES"))) {
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 0x0026, NULL, 0, osPath))) { // CSIDL_PROGRAM_FILES (%PROGRAMFILES%)
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("PROGRAMFILESX86")) || qbs_equal(qbs_ucase(context), qbs_new_txt("PROGRAMFILES X86")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("PROGRAM FILES X86")) || qbs_equal(qbs_ucase(context), qbs_new_txt("PROGRAM FILES 86")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("PROGRAM FILES (X86)")) || qbs_equal(qbs_ucase(context), qbs_new_txt("PROGRAMFILES (X86)")) ||
|
||||
qbs_equal(qbs_ucase(context), qbs_new_txt("PROGRAM FILES(X86)"))) {
|
||||
#ifdef QB64_WINDOWS &&_WIN64
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 0x002a, NULL, 0, osPath))) { // CSIDL_PROGRAM_FILES (%PROGRAMFILES(X86)%)
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (qbs_equal(qbs_ucase(context), qbs_new_txt("TEMP")) || qbs_equal(qbs_ucase(context), qbs_new_txt("TEMP FILES"))) {
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH + 1];
|
||||
DWORD pathlen;
|
||||
pathlen = GetTempPathA(261, osPath); //%TEMP%
|
||||
char path[pathlen];
|
||||
memcpy(path, &osPath, pathlen);
|
||||
if (pathlen > 0) {
|
||||
return qbs_new_txt(path);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
// general fallback location
|
||||
#ifdef QB64_WINDOWS
|
||||
CHAR osPath[MAX_PATH];
|
||||
if (SUCCEEDED(SHGetFolderPathA(NULL, 0, NULL, 0, osPath))) { // desktop
|
||||
return qbs_add(qbs_new_txt(osPath), qbs_new_txt("\\"));
|
||||
}
|
||||
return qbs_new_txt(".\\"); // current location
|
||||
#else
|
||||
return qbs_new_txt("./"); // current location
|
||||
#endif
|
||||
}
|
||||
|
||||
int32 func__direxists(qbs *file) {
|
||||
if (new_error)
|
||||
return 0;
|
||||
static qbs *strz = NULL;
|
||||
if (!strz)
|
||||
strz = qbs_new(0, 0);
|
||||
qbs_set(strz, qbs_add(file, qbs_new_txt_len("\0", 1)));
|
||||
#ifdef QB64_WINDOWS
|
||||
static int32 x;
|
||||
x = GetFileAttributes(fixdir(strz));
|
||||
if (x == INVALID_FILE_ATTRIBUTES)
|
||||
return 0;
|
||||
if (x & FILE_ATTRIBUTE_DIRECTORY)
|
||||
return -1;
|
||||
return 0;
|
||||
#elif defined(QB64_UNIX)
|
||||
struct stat sb;
|
||||
if (stat(fixdir(strz), &sb) == 0 && S_ISDIR(sb.st_mode))
|
||||
return -1;
|
||||
return 0;
|
||||
#else
|
||||
return 0; // default response
|
||||
#endif
|
||||
}
|
||||
|
||||
int32 func__fileexists(qbs *file) {
|
||||
if (new_error)
|
||||
return 0;
|
||||
static qbs *strz = NULL;
|
||||
if (!strz)
|
||||
strz = qbs_new(0, 0);
|
||||
qbs_set(strz, qbs_add(file, qbs_new_txt_len("\0", 1)));
|
||||
#ifdef QB64_WINDOWS
|
||||
static int32 x;
|
||||
x = GetFileAttributes(fixdir(strz));
|
||||
if (x == INVALID_FILE_ATTRIBUTES)
|
||||
return 0;
|
||||
if (x & FILE_ATTRIBUTE_DIRECTORY)
|
||||
return 0;
|
||||
return -1;
|
||||
#elif defined(QB64_UNIX)
|
||||
struct stat sb;
|
||||
if (stat(fixdir(strz), &sb) == 0 && S_ISREG(sb.st_mode))
|
||||
return -1;
|
||||
return 0;
|
||||
#else
|
||||
// generic method (not currently used)
|
||||
static std::ifstream fh;
|
||||
fh.open(fixdir(strz), std::ios::binary | std::ios::in);
|
||||
if (fh.is_open() == NULL) {
|
||||
fh.clear(std::ios::goodbit);
|
||||
return 0;
|
||||
}
|
||||
fh.clear(std::ios::goodbit);
|
||||
fh.close();
|
||||
return -1;
|
||||
#endif
|
||||
}
|
||||
|
||||
qbs *startDir = NULL; // set on startup
|
||||
|
||||
qbs *func__startdir() {
|
||||
qbs *temp = qbs_new(0, 1);
|
||||
qbs_set(temp, startDir);
|
||||
return temp;
|
||||
}
|
||||
|
||||
void sub_chdir(qbs *str) {
|
||||
|
||||
if (new_error)
|
||||
return;
|
||||
static qbs *strz = NULL;
|
||||
if (!strz)
|
||||
strz = qbs_new(0, 0);
|
||||
qbs_set(strz, qbs_add(str, qbs_new_txt_len("\0", 1)));
|
||||
if (chdir(fixdir(strz)) == -1) {
|
||||
// assume errno==ENOENT
|
||||
error(76); // path not found
|
||||
}
|
||||
|
||||
static int32 tmp_long;
|
||||
static int32 got_ports = 0;
|
||||
}
|
||||
|
||||
void sub_files(qbs *str, int32 passed) {
|
||||
if (new_error)
|
||||
return;
|
||||
|
||||
static int32 i, i2, i3;
|
||||
static qbs *strz = NULL;
|
||||
if (!strz)
|
||||
strz = qbs_new(0, 0);
|
||||
|
||||
if (passed) {
|
||||
qbs_set(strz, qbs_add(str, qbs_new_txt_len("\0", 1)));
|
||||
} else {
|
||||
qbs_set(strz, qbs_new_txt_len("\0", 1));
|
||||
}
|
||||
|
||||
#ifdef QB64_WINDOWS
|
||||
static WIN32_FIND_DATA fd;
|
||||
static HANDLE hFind;
|
||||
static qbs *strpath = NULL;
|
||||
if (!strpath)
|
||||
strpath = qbs_new(0, 0);
|
||||
static qbs *strz2 = NULL;
|
||||
if (!strz2)
|
||||
strz2 = qbs_new(0, 0);
|
||||
|
||||
i = 0;
|
||||
if (strz->len >= 2) {
|
||||
if (strz->chr[strz->len - 2] == 92)
|
||||
i = 1;
|
||||
} else
|
||||
i = 1;
|
||||
if (i) { // add * (and new NULL term.)
|
||||
strz->chr[strz->len - 1] = 42; //"*"
|
||||
qbs_set(strz, qbs_add(strz, qbs_new_txt_len("\0", 1)));
|
||||
}
|
||||
|
||||
qbs_set(strpath, strz);
|
||||
|
||||
for (i = strpath->len; i > 0; i--) {
|
||||
if ((strpath->chr[i - 1] == 47) || (strpath->chr[i - 1] == 92)) {
|
||||
strpath->len = i;
|
||||
break;
|
||||
}
|
||||
} // i
|
||||
if (i == 0)
|
||||
strpath->len = 0; // no path specified
|
||||
|
||||
// print the current path
|
||||
// note: for QBASIC compatibility reasons it does not print the directory name of the files being displayed
|
||||
static uint8 curdir[4096];
|
||||
static uint8 curdir2[4096];
|
||||
i2 = GetCurrentDirectory(4096, (char *)curdir);
|
||||
if (i2) {
|
||||
i2 = GetShortPathName((char *)curdir, (char *)curdir2, 4096);
|
||||
if (i2) {
|
||||
qbs_set(strz2, qbs_ucase(qbs_new_txt_len((char *)curdir2, i2)));
|
||||
qbs_print(strz2, 1);
|
||||
} else {
|
||||
error(5);
|
||||
return;
|
||||
}
|
||||
} else {
|
||||
error(5);
|
||||
return;
|
||||
}
|
||||
|
||||
hFind = FindFirstFile(fixdir(strz), &fd);
|
||||
if (hFind == INVALID_HANDLE_VALUE) {
|
||||
error(53);
|
||||
return;
|
||||
} // file not found
|
||||
do {
|
||||
|
||||
if (!fd.cAlternateFileName[0]) { // no alternate filename exists
|
||||
qbs_set(strz2, qbs_ucase(qbs_new_txt_len(fd.cFileName, strlen(fd.cFileName))));
|
||||
} else {
|
||||
qbs_set(strz2, qbs_ucase(qbs_new_txt_len(fd.cAlternateFileName, strlen(fd.cAlternateFileName))));
|
||||
}
|
||||
|
||||
if (strz2->len < 12) { // padding required
|
||||
qbs_set(strz2, qbs_add(strz2, func_space(12 - strz2->len)));
|
||||
i2 = 0;
|
||||
for (i = 0; i < 12; i++) {
|
||||
if (strz2->chr[i] == 46) {
|
||||
memmove(&strz2->chr[8], &strz2->chr[i], 4);
|
||||
memset(&strz2->chr[i], 32, 8 - i);
|
||||
break;
|
||||
}
|
||||
} // i
|
||||
} // padding
|
||||
|
||||
// add " " or "<DIR> "
|
||||
if (fd.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) {
|
||||
qbs_set(strz2, qbs_add(strz2, qbs_new_txt_len("<DIR> ", 6)));
|
||||
} else {
|
||||
qbs_set(strz2, qbs_add(strz2, func_space(6)));
|
||||
}
|
||||
|
||||
makefit(strz2);
|
||||
qbs_print(strz2, 0);
|
||||
|
||||
} while (FindNextFile(hFind, &fd));
|
||||
FindClose(hFind);
|
||||
|
||||
static ULARGE_INTEGER FreeBytesAvailableToCaller;
|
||||
static ULARGE_INTEGER TotalNumberOfBytes;
|
||||
static ULARGE_INTEGER TotalNumberOfFreeBytes;
|
||||
static int64 bytes;
|
||||
static char *cp;
|
||||
qbs_set(strpath, qbs_add(strpath, qbs_new_txt_len("\0", 1)));
|
||||
cp = (char *)strpath->chr;
|
||||
if (strpath->len == 1)
|
||||
cp = NULL;
|
||||
if (GetDiskFreeSpaceEx(cp, &FreeBytesAvailableToCaller, &TotalNumberOfBytes, &TotalNumberOfFreeBytes)) {
|
||||
bytes = *(int64 *)(void *)&FreeBytesAvailableToCaller;
|
||||
} else {
|
||||
bytes = 0;
|
||||
}
|
||||
if (func_pos(NULL) > 1) {
|
||||
strz2->len = 0;
|
||||
qbs_print(strz2, 1);
|
||||
} // new line if necessary
|
||||
qbs_set(strz2, qbs_add(qbs_str(bytes), qbs_new_txt_len(" Bytes free", 11)));
|
||||
qbs_print(strz2, 1);
|
||||
|
||||
#endif
|
||||
}
|
||||
|
||||
void sub_kill(qbs *str) {
|
||||
// note: file not found returned for non-existant paths too
|
||||
// file already open returned if access unavailable
|
||||
if (new_error)
|
||||
return;
|
||||
static int32 i;
|
||||
static qbs *strz = NULL;
|
||||
if (!strz)
|
||||
strz = qbs_new(0, 0);
|
||||
qbs_set(strz, qbs_add(str, qbs_new_txt_len("\0", 1)));
|
||||
#ifdef QB64_WINDOWS
|
||||
static WIN32_FIND_DATA fd;
|
||||
static HANDLE hFind;
|
||||
static qbs *strpath = NULL;
|
||||
if (!strpath)
|
||||
strpath = qbs_new(0, 0);
|
||||
static qbs *strfullz = NULL;
|
||||
if (!strfullz)
|
||||
strfullz = qbs_new(0, 0);
|
||||
// find path
|
||||
qbs_set(strpath, strz);
|
||||
for (i = strpath->len; i > 0; i--) {
|
||||
if ((strpath->chr[i - 1] == 47) || (strpath->chr[i - 1] == 92)) {
|
||||
strpath->len = i;
|
||||
break;
|
||||
}
|
||||
} // i
|
||||
if (i == 0)
|
||||
strpath->len = 0; // no path specified
|
||||
static int32 count;
|
||||
count = 0;
|
||||
hFind = FindFirstFile(fixdir(strz), &fd);
|
||||
if (hFind == INVALID_HANDLE_VALUE) {
|
||||
error(53);
|
||||
return;
|
||||
} // file not found
|
||||
do {
|
||||
if ((fd.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) == 0) {
|
||||
qbs_set(strfullz, qbs_add(strpath, qbs_new_txt_len(fd.cFileName, strlen(fd.cFileName) + 1)));
|
||||
if (!DeleteFile((char *)strfullz->chr)) {
|
||||
i = GetLastError();
|
||||
if ((i == 5) || (i == 19) || (i == 33) || (i == 32)) {
|
||||
FindClose(hFind);
|
||||
error(55);
|
||||
return;
|
||||
} // file already open
|
||||
FindClose(hFind);
|
||||
error(53);
|
||||
return; // file not found
|
||||
}
|
||||
count++;
|
||||
} // not a directory
|
||||
} while (FindNextFile(hFind, &fd));
|
||||
FindClose(hFind);
|
||||
if (!count) {
|
||||
error(53);
|
||||
return;
|
||||
} // file not found
|
||||
return;
|
||||
#else
|
||||
if (remove(fixdir(strz))) {
|
||||
i = errno;
|
||||
if (i == ENOENT) {
|
||||
error(53);
|
||||
return;
|
||||
} // file not found
|
||||
if (i == EACCES) {
|
||||
error(75);
|
||||
return;
|
||||
} // path/file access error
|
||||
error(64); // bad file name (assumed)
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
void sub_mkdir(qbs *str) {
|
||||
if (new_error)
|
||||
return;
|
||||
static qbs *strz = NULL;
|
||||
if (!strz)
|
||||
strz = qbs_new(0, 0);
|
||||
qbs_set(strz, qbs_add(str, qbs_new_txt_len("\0", 1)));
|
||||
#ifdef QB64_UNIX
|
||||
if (mkdir(fixdir(strz), 0770) == -1) {
|
||||
#else
|
||||
if (mkdir(fixdir(strz)) == -1) {
|
||||
#endif
|
||||
if (errno == EEXIST) {
|
||||
error(75);
|
||||
return;
|
||||
} // path/file access error
|
||||
// assume errno==ENOENT
|
||||
error(76); // path not found
|
||||
}
|
||||
}
|
||||
|
||||
void sub_name(qbs *oldname, qbs *newname) {
|
||||
if (new_error)
|
||||
return;
|
||||
static qbs *strz = NULL;
|
||||
if (!strz)
|
||||
strz = qbs_new(0, 0);
|
||||
static qbs *strz2 = NULL;
|
||||
if (!strz2)
|
||||
strz2 = qbs_new(0, 0);
|
||||
static int32 i;
|
||||
qbs_set(strz, qbs_add(oldname, qbs_new_txt_len("\0", 1)));
|
||||
qbs_set(strz2, qbs_add(newname, qbs_new_txt_len("\0", 1)));
|
||||
if (rename(fixdir(strz), fixdir(strz2))) {
|
||||
i = errno;
|
||||
if (i == ENOENT) {
|
||||
error(53);
|
||||
return;
|
||||
} // file not found
|
||||
if (i == EINVAL) {
|
||||
error(64);
|
||||
return;
|
||||
} // bad file name
|
||||
if (i == EACCES) {
|
||||
error(75);
|
||||
return;
|
||||
} // path/file access error
|
||||
error(5); // Illegal function call (assumed)
|
||||
}
|
||||
}
|
||||
|
||||
void sub_rmdir(qbs *str) {
|
||||
if (new_error)
|
||||
return;
|
||||
static qbs *strz = NULL;
|
||||
if (!strz)
|
||||
strz = qbs_new(0, 0);
|
||||
qbs_set(strz, qbs_add(str, qbs_new_txt_len("\0", 1)));
|
||||
if (rmdir(fixdir(strz)) == -1) {
|
||||
if (errno == ENOTEMPTY) {
|
||||
error(75);
|
||||
return;
|
||||
} // path/file access error
|
||||
// assume errno==ENOENT
|
||||
error(76); // path not found
|
||||
}
|
||||
}
|
|
@ -3,11 +3,13 @@
|
|||
#include "compression.h"
|
||||
#include "datetime.h"
|
||||
#include "event.h"
|
||||
#include "extended_math.h"
|
||||
#include "filepath.h"
|
||||
#include "filesystem.h"
|
||||
#include "font.h"
|
||||
#include "gui.h"
|
||||
#include "image.h"
|
||||
#include "rounding.h"
|
||||
#include "extended_math.h"
|
||||
|
||||
extern int32 func__cinp(int32 toggle,
|
||||
int32 passed); // Console INP scan code reader
|
||||
|
@ -88,14 +90,9 @@ void requestKeyboardOverlayImage(int32 handle) {
|
|||
|
||||
// extern functions
|
||||
|
||||
extern qbs *func__dir(qbs *context);
|
||||
|
||||
extern int32 func__scaledwidth();
|
||||
extern int32 func__scaledheight();
|
||||
|
||||
extern qbs *func__cwd();
|
||||
extern qbs *func__startdir();
|
||||
|
||||
extern void sub__fps(double fps, int32 passed);
|
||||
|
||||
extern void sub__resize(int32 on_off, int32 stretch_smooth);
|
||||
|
@ -176,8 +173,6 @@ extern int32 func_windowexists();
|
|||
extern int32 func_screenicon();
|
||||
extern int32 func_screenwidth();
|
||||
extern int32 func_screenheight();
|
||||
extern int32 func__borderwidth();
|
||||
extern int32 func__titlebarheight();
|
||||
extern void sub_screenicon();
|
||||
extern void sub__console(int32);
|
||||
extern int32 func__console();
|
||||
|
@ -189,8 +184,6 @@ extern int32 func__hasfocus();
|
|||
extern void set_foreground_window(ptrszint i);
|
||||
extern qbs *func__title();
|
||||
extern int32 func__handle();
|
||||
extern int32 func__fileexists(qbs *);
|
||||
extern int32 func__direxists(qbs *);
|
||||
extern int32 func_stick(int32 i, int32 axis_group, int32 passed);
|
||||
extern int32 func_strig(int32 i, int32 controller, int32 passed);
|
||||
extern void sub__maptriangle(int32 cull_options, float sx1, float sy1,
|
||||
|
@ -222,7 +215,6 @@ extern void field_get(int32 fileno, int64 seekpos, int32 passed);
|
|||
extern void field_put(int32 fileno, int64 seekpos, int32 passed);
|
||||
extern int32 func__keydown(int32 x);
|
||||
extern int32 func__keyhit();
|
||||
extern void sub_files(qbs *str, int32 passed);
|
||||
extern int32 func_lpos(int32);
|
||||
extern void sub__printimage(int32 i);
|
||||
extern float func__mousemovementx(int32 context, int32 passed);
|
||||
|
@ -244,7 +236,6 @@ extern qbs *func__clipboard();
|
|||
extern int32 func__clipboardimage();
|
||||
extern void sub__clipboardimage(int32 src);
|
||||
extern int32 func__exit();
|
||||
extern char *fixdir(qbs *);
|
||||
extern void revert_input_check();
|
||||
extern int32 func__openhost(qbs *);
|
||||
extern int32 func__openconnection(int32);
|
||||
|
@ -274,7 +265,6 @@ extern void sub__putimage(double f_dx1, double f_dy1, double f_dx2,
|
|||
double f_sy1, double f_sx2, double f_sy2,
|
||||
int32 passed);
|
||||
extern int32 selectfont(int32 f, img_struct *im);
|
||||
extern void sndsetup();
|
||||
extern uint32 sib();
|
||||
extern uint32 sib_mod0();
|
||||
extern uint8 *rm8();
|
||||
|
@ -297,10 +287,6 @@ extern void sub_defseg(int32 segment, int32 passed);
|
|||
extern int32 func_peek(int32 offset);
|
||||
extern void sub_poke(int32 offset, int32 value);
|
||||
extern void more_return_points();
|
||||
extern void qb64_generatesound(double f, double l, uint8 wait);
|
||||
extern uint8 *soundwave(double frequency, double length, double volume,
|
||||
double fadein, double fadeout);
|
||||
extern int32 wavesize(double length);
|
||||
extern qbs *qbs_new_descriptor();
|
||||
extern void qbs_free_descriptor(qbs *str);
|
||||
extern void qbs_free(qbs *str);
|
||||
|
@ -522,14 +508,8 @@ extern qbs *func_input(int32 n, int32 i, int32 passed);
|
|||
extern int32 func__statusCode(int32 handle);
|
||||
|
||||
extern double func_sqr(double value);
|
||||
extern void snd_check();
|
||||
extern qbs *func_command(int32 index, int32 passed);
|
||||
extern int32 func__commandcount();
|
||||
extern void sub_kill(qbs *str);
|
||||
extern void sub_name(qbs *oldname, qbs *newname);
|
||||
extern void sub_chdir(qbs *str);
|
||||
extern void sub_mkdir(qbs *str);
|
||||
extern void sub_rmdir(qbs *str);
|
||||
extern long double pow2(long double x, long double y);
|
||||
extern int32 func_freefile();
|
||||
extern void sub__mousehide();
|
||||
|
|
Loading…
Reference in a new issue