clean up directory entries
This commit is contained in:
parent
7fcd7ad635
commit
1998e6cccc
|
@ -76,26 +76,62 @@ reset(UxnFile *c)
|
|||
}
|
||||
|
||||
static Uint16
|
||||
get_entry(char *p, Uint16 len, const char *pathname, const char *basename, int fail_nonzero)
|
||||
stat_fill(Uint16 addr, Uint16 len, char c)
|
||||
{
|
||||
struct stat st;
|
||||
if(len < strlen(basename) + 8)
|
||||
return 0;
|
||||
if(stat(pathname, &st))
|
||||
return fail_nonzero ? snprintf(p, len, "!!!! %s\n", basename) : 0;
|
||||
else if(S_ISDIR(st.st_mode))
|
||||
return snprintf(p, len, "---- %s/\n", basename);
|
||||
else if(st.st_size < 0x10000)
|
||||
return snprintf(p, len, "%04x %s\n", (unsigned int)st.st_size, basename);
|
||||
else
|
||||
return snprintf(p, len, "???? %s\n", basename);
|
||||
Uint16 i;
|
||||
for (i = 0; i < len; i++)
|
||||
uxn.ram[(addr + i) & 0xffff] = c;
|
||||
return len;
|
||||
}
|
||||
|
||||
static Uint16
|
||||
file_read_dir(UxnFile *c, char *dest, Uint16 len)
|
||||
stat_size(Uint16 addr, Uint16 len, off_t size)
|
||||
{
|
||||
Uint16 i;
|
||||
for (i = 1; i <= len; i++) {
|
||||
char c = '0' + (Uint8)(size & 0xf);
|
||||
uxn.ram[(addr + len - i) & 0xffff] = c;
|
||||
size = size >> 4;
|
||||
}
|
||||
if (size > 0)
|
||||
stat_fill(addr, len, '?');
|
||||
return len;
|
||||
}
|
||||
|
||||
static Uint16
|
||||
stat_entry(Uint16 addr, char sym, off_t size, const char *s)
|
||||
{
|
||||
Uint16 pos = addr;
|
||||
pos += sym ? stat_fill(pos, 4, sym) : stat_size(pos, 4, size);
|
||||
uxn.ram[(pos++) & 0xffff] = ' ';
|
||||
while(*s)
|
||||
uxn.ram[(pos++) & 0xffff] = *(s++);
|
||||
uxn.ram[(pos++) & 0xffff] = '\n';
|
||||
/* like printf and friends, we don't count the trailing null */
|
||||
uxn.ram[pos & 0xffff] = '\0';
|
||||
return pos - addr;
|
||||
}
|
||||
|
||||
static Uint16
|
||||
get_entry(Uint16 addr, Uint16 len, const char *pathname, const char *basename)
|
||||
{
|
||||
struct stat st;
|
||||
if(len < strlen(basename) + 8) return 0;
|
||||
char sym = 0;
|
||||
off_t size = 0;
|
||||
if(stat(pathname, &st)) sym = '!';
|
||||
else if(S_ISDIR(st.st_mode)) sym = '-';
|
||||
else if(st.st_size >= 0x10000) sym = '?';
|
||||
else size = st.st_size;
|
||||
return stat_entry(addr, sym, size, basename);
|
||||
}
|
||||
|
||||
static Uint16
|
||||
file_read_dir(UxnFile *c, Uint16 addr, Uint16 len)
|
||||
{
|
||||
static char pathname[4352];
|
||||
char *p = dest;
|
||||
Uint16 pos = addr;
|
||||
char cwd[PATH_MAX] = {'\0'}, *t;
|
||||
if(c->de == NULL) c->de = readdir(c->dir);
|
||||
for(; c->de != NULL; c->de = readdir(c->dir)) {
|
||||
Uint16 n;
|
||||
|
@ -103,7 +139,6 @@ file_read_dir(UxnFile *c, char *dest, Uint16 len)
|
|||
continue;
|
||||
if(strcmp(c->de->d_name, "..") == 0) {
|
||||
/* hide "sandbox/.." */
|
||||
char cwd[PATH_MAX] = {'\0'}, *t;
|
||||
/* Note there's [currently] no way of chdir()ing from uxn, so $PWD
|
||||
* is always the sandbox top level. */
|
||||
getcwd(cwd, sizeof(cwd));
|
||||
|
@ -119,12 +154,12 @@ file_read_dir(UxnFile *c, char *dest, Uint16 len)
|
|||
snprintf(pathname, sizeof(pathname), "%s/%s", c->current_filename, c->de->d_name);
|
||||
else
|
||||
pathname[0] = '\0';
|
||||
n = get_entry(p, len, pathname, c->de->d_name, 1);
|
||||
n = get_entry(pos, len, pathname, c->de->d_name);
|
||||
if(!n) break;
|
||||
p += n;
|
||||
pos += n;
|
||||
len -= n;
|
||||
}
|
||||
return p - dest;
|
||||
return pos - addr;
|
||||
}
|
||||
|
||||
static char *
|
||||
|
@ -221,7 +256,7 @@ file_read(UxnFile *c, Uint16 addr, int len)
|
|||
if(c->state == FILE_READ)
|
||||
return file_read_file(addr, len, c->f);
|
||||
if(c->state == DIR_READ)
|
||||
return file_read_dir(c, (char *)&uxn.ram[addr], len);
|
||||
return file_read_dir(c, addr, len);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -293,27 +328,6 @@ file_write(UxnFile *c, Uint16 addr, Uint16 len, Uint8 flags)
|
|||
return ret;
|
||||
}
|
||||
|
||||
static Uint16
|
||||
stat_fill(Uint16 addr, Uint16 len, char c)
|
||||
{
|
||||
Uint16 i;
|
||||
for (i = 0; i < len; i++)
|
||||
uxn.ram[(addr + i) & 0xffff] = c;
|
||||
return len;
|
||||
}
|
||||
|
||||
static Uint16
|
||||
stat_size(Uint16 addr, Uint16 len, off_t size)
|
||||
{
|
||||
Uint16 i;
|
||||
for (i = 1; i <= len; i++) {
|
||||
char c = '0' + (Uint8)(size & 0xf);
|
||||
uxn.ram[(addr + len - i) & 0xffff] = c;
|
||||
size = size >> 4;
|
||||
}
|
||||
return size == 0 ? len : stat_fill(addr, len, '?');
|
||||
}
|
||||
|
||||
static Uint16
|
||||
file_stat(UxnFile *c, Uint16 addr, Uint16 len)
|
||||
{
|
||||
|
|
Loading…
Reference in New Issue