summaryrefslogtreecommitdiff
path: root/Source/Kernel/VFS
diff options
context:
space:
mode:
Diffstat (limited to 'Source/Kernel/VFS')
-rw-r--r--Source/Kernel/VFS/FSNode-sc.proto.cpp4
-rw-r--r--Source/Kernel/VFS/File-sc.class.cpp68
-rw-r--r--Source/Kernel/VFS/File.class.cpp29
-rw-r--r--Source/Kernel/VFS/File.class.h39
-rw-r--r--Source/Kernel/VFS/FileNode.class.h2
-rw-r--r--Source/Kernel/VFS/TextFile.class.cpp21
-rw-r--r--Source/Kernel/VFS/TextFile.class.h21
-rw-r--r--Source/Kernel/VFS/VFS.ns.cpp43
-rw-r--r--Source/Kernel/VFS/VFS.ns.h5
9 files changed, 121 insertions, 111 deletions
diff --git a/Source/Kernel/VFS/FSNode-sc.proto.cpp b/Source/Kernel/VFS/FSNode-sc.proto.cpp
index 279303b..717ccef 100644
--- a/Source/Kernel/VFS/FSNode-sc.proto.cpp
+++ b/Source/Kernel/VFS/FSNode-sc.proto.cpp
@@ -35,9 +35,9 @@ u32int FSNode::scall(u8int wat, u32int a, u32int b, u32int c, u32int d) {
String* path = (String*)a;
FSNode* n;
if (b == 0) {
- n = VFS::mkdir(*path);
+ n = VFS::createDirectory(*path, 0, true);
} else {
- n = VFS::mkdir(*path, Res::get<DirectoryNode>(b, FNIF_OBJTYPE));
+ n = VFS::createDirectory(*path, Res::get<DirectoryNode>(b, FNIF_OBJTYPE), true);
}
if (n != 0) return n->resId();
}
diff --git a/Source/Kernel/VFS/File-sc.class.cpp b/Source/Kernel/VFS/File-sc.class.cpp
new file mode 100644
index 0000000..e5e8e25
--- /dev/null
+++ b/Source/Kernel/VFS/File-sc.class.cpp
@@ -0,0 +1,68 @@
+#include "File.class.h"
+#include <VFS/VFS.ns.h>
+#include <TaskManager/Task.ns.h>
+#include <FSNode.iface.h>
+#include <SyscallManager/Res.ns.h>
+
+u32int File::scall(u8int wat, u32int a, u32int b, u32int c, u32int d) {
+ if (wat == FLIF_SOPEN) {
+ String* name = (String*)a;
+ FSNode* start = Res::get<FSNode>(c, FNIF_OBJTYPE);
+ File* f = new File();
+ if (!f->open(*name, b, start, true)) {
+ delete f;
+ } else {
+ return f->resId();
+ }
+ }
+ return (u32int) - 1;
+}
+
+u32int File::closeSC() {
+ if (!valid()) return 1;
+ close();
+ return 0;
+}
+
+u32int File::validSC() {
+ return (valid() ? 1 : 0);
+}
+
+u32int File::readSC(u32int max_length, u32int ptr) {
+ if (!m_file->readable()) return 0;
+ return read(max_length, (u8int*)ptr);
+}
+
+u32int File::writeSC(u32int length, u32int ptr) {
+ if (!m_file->writable()) return 0;
+ return (write(length, (u8int*)ptr) ? 1 : 0);
+}
+
+u32int File::seekSC(u32int counta, u32int countb, u32int mode) {
+ union {
+ u32int a[2];
+ u64int x;
+ } wat = {{counta, countb}};
+ return (seek(wat.x, mode) ? 1 : 0);
+}
+
+u32int File::positionSC() {
+ u64int* w = (u64int*)Mem::mkXchgSpace(sizeof(u64int));
+ *w = position();
+ return (u32int)w;
+}
+
+u32int File::lengthSC() {
+ u64int* w = (u64int*)Mem::mkXchgSpace(sizeof(u64int));
+ *w = length();
+ return (u32int)w;
+}
+
+u32int File::eofSC() {
+ return (eof() ? 1 : 0);
+}
+
+bool File::accessible() {
+ if (ISROOT or Usr::uid() == m_process->getUid()) return true;
+ return false;
+}
diff --git a/Source/Kernel/VFS/File.class.cpp b/Source/Kernel/VFS/File.class.cpp
index fbaabbe..c5ddcd6 100644
--- a/Source/Kernel/VFS/File.class.cpp
+++ b/Source/Kernel/VFS/File.class.cpp
@@ -2,11 +2,23 @@
#include <VFS/VFS.ns.h>
#include <TaskManager/Task.ns.h>
-File::File() : m_file(NULL), m_valid(false), m_writable(false), m_position(0) {
+call_t File::m_callTable[] = {
+ CALL0(FLIF_CLOSE, &File::closeSC),
+ CALL0(FLIF_VALID, &File::validSC),
+ CALL2(FLIF_READ, &File::readSC),
+ CALL2(FLIF_WRITE, &File::writeSC),
+ CALL3(FLIF_SEEK, &File::seekSC),
+ CALL0(FLIF_POSITION, &File::positionSC),
+ CALL0(FLIF_LENGTH, &File::lengthSC),
+ CALL0(FLIF_EOF, &File::eofSC),
+ CALL0(0, 0)
+};
+
+File::File() : Ressource(FLIF_OBJTYPE, m_callTable), m_file(NULL), m_valid(false), m_writable(false), m_position(0) {
}
File::File(String filename, u8int mode, FSNode* start) :
- m_file(NULL), m_valid(false), m_writable(false), m_position(0) {
+ Ressource(FLIF_OBJTYPE, m_callTable), m_file(NULL), m_valid(false), m_writable(false), m_position(0) {
open(filename, mode, start);
}
@@ -14,13 +26,13 @@ File::~File() {
close();
}
-bool File::open(String filename, u8int mode, FSNode* start) {
+bool File::open(String filename, u8int mode, FSNode* start, bool vrfyperm) {
if (m_valid) return false;
FSNode* node = VFS::find(filename, start);
if (node == NULL){
if (mode == FM_READ) return false;
- node = VFS::createFile(filename, start);
+ node = VFS::createFile(filename, start, vrfyperm);
if (node == 0) return false;
}
if (node->type() != NT_FILE) return false;
@@ -28,7 +40,9 @@ bool File::open(String filename, u8int mode, FSNode* start) {
m_file = (FileNode*) node;
m_writable = (mode != FM_READ);
- if (!m_file->writable() and m_writable) return false;
+ if (vrfyperm and m_writable and !m_file->writable()) return false;
+ if (vrfyperm and !m_file->readable()) return false;
+ if (!m_file->fsWritable() and m_writable) return false;
if (mode == FM_READ or mode == FM_REPLACE) {
m_position = 0;
@@ -44,7 +58,8 @@ bool File::open(String filename, u8int mode, FSNode* start) {
else
m_file->m_writers++;
- Task::currProcess()->registerFileDescriptor(this);
+ m_process = Task::currProcess();
+ m_process->registerFileDescriptor(this);
m_valid = true;
return true;
}
@@ -135,5 +150,5 @@ void File::close(bool unregisterFD) {
m_file = NULL;
m_position = 0;
m_writable = false;
- if (unregisterFD) Task::currProcess()->unregisterFileDescriptor(this);
+ if (unregisterFD) m_process->unregisterFileDescriptor(this);
}
diff --git a/Source/Kernel/VFS/File.class.h b/Source/Kernel/VFS/File.class.h
index f5d0c56..00b92b6 100644
--- a/Source/Kernel/VFS/File.class.h
+++ b/Source/Kernel/VFS/File.class.h
@@ -3,35 +3,40 @@
#include <VFS/FileNode.class.h>
#include <ByteArray.class.h>
+#include <File.iface.h>
+#include <SyscallManager/Ressource.class.h>
+class Process;
-enum {
- FM_READ = 0, //Open for read, put cursor at beginning
- FM_TRUNCATE = 1, //Open for write, truncating file before
- FM_APPEND = 2, //Open for write, put cursor at end
- FM_REPLACE = 3 //Open for write, put cursor at beginning
-};
-
-enum {
- SM_FORWARD = 0, //Seek from actual position
- SM_BACKWARD = 1, //Seek from actual position, backward
- SM_BEGINNING = 2, //Seek from start of file
- SM_END = 3, //Seek from end of file
-};
-
-class File {
+class File : public Ressource {
protected:
FileNode* m_file;
bool m_valid; //Is a file opened and valid ?
bool m_writable; //Is file opened for write ?
u64int m_position;
+ Process* m_process;
+
+ //Syscalls
+ static call_t m_callTable[];
+ u32int closeSC();
+ u32int validSC();
+ u32int readSC(u32int, u32int);
+ u32int writeSC(u32int, u32int);
+ u32int seekSC(u32int, u32int, u32int);
+ u32int positionSC();
+ u32int lengthSC();
+ u32int eofSC();
+ bool accessible();
public:
+ static u32int scall(u8int, u32int, u32int, u32int, u32int);
+
File();
File(String filename, u8int mode = FM_READ, FSNode* start = 0);
virtual ~File();
- bool open(String filename, u8int mode = FM_READ, FSNode* start = 0);
+ bool open(String filename, u8int mode = FM_READ, FSNode* start = 0, bool vrfyperm = false);
void close(bool unregisterFD = true); //unregisterFD = whether or not we must unregister the file descriptor from process
+ bool valid() { return m_valid; }
u32int read(u32int max_length, u8int *data);
bool write(u32int length, u8int *data);
@@ -49,8 +54,6 @@ class File {
u64int position() { return m_position; }
u64int length() { return m_file->getLength(); }
bool eof();
-
- bool valid() { return m_valid; }
};
#endif
diff --git a/Source/Kernel/VFS/FileNode.class.h b/Source/Kernel/VFS/FileNode.class.h
index 7ab617f..e99ef5e 100644
--- a/Source/Kernel/VFS/FileNode.class.h
+++ b/Source/Kernel/VFS/FileNode.class.h
@@ -19,7 +19,7 @@ class FileNode : public FSNode {
u8int type() { return NT_FILE; }
bool removable() { return true; }
bool used() { return (m_readers != 0 or m_writers != 0); }
- bool writable() { return m_fs->isWritable(); }
+ bool fsWritable() { return m_fs->isWritable(); }
u32int read(u64int position, u32int max_length, u8int *data) {
return m_fs->read(this, position, max_length, data);
diff --git a/Source/Kernel/VFS/TextFile.class.cpp b/Source/Kernel/VFS/TextFile.class.cpp
deleted file mode 100644
index a877392..0000000
--- a/Source/Kernel/VFS/TextFile.class.cpp
+++ /dev/null
@@ -1,21 +0,0 @@
-#include "TextFile.class.h"
-
-bool TextFile::write(String str, bool addnl) {
- ByteArray a(str, m_encoding);
- if (addnl) a += (u8int)'\n';
- return File::write(a);
-}
-
-String TextFile::readLine(char separator) {
- ByteArray buffer;
- while (1) {
- char c;
- if (read(1, (u8int*)&c) == 0) {
- return buffer.toString(m_encoding);
- }
- if (c == separator) {
- return buffer.toString(m_encoding);
- }
- buffer += (u8int)c;
- }
-}
diff --git a/Source/Kernel/VFS/TextFile.class.h b/Source/Kernel/VFS/TextFile.class.h
deleted file mode 100644
index a0cd505..0000000
--- a/Source/Kernel/VFS/TextFile.class.h
+++ /dev/null
@@ -1,21 +0,0 @@
-#ifndef DEF_TEXTFILE_CLASS_H
-#define DEF_TEXTFILE_CLASS_H
-
-#include <VFS/File.class.h>
-
-class TextFile : public File {
- private:
- u8int m_encoding;
-
- public:
- TextFile(u8int encoding = UE_UTF8) : File() { m_encoding = encoding; }
- TextFile(String filename, u8int mode = FM_READ, FSNode* start = 0, u8int encoding = UE_UTF8)
- : File(filename, mode, start) { m_encoding = encoding; }
- ~TextFile() {}
-
- void setEncoding(u8int encoding = UE_UTF8) { m_encoding = encoding; }
- bool write(String str, bool addnl = false); // Addnl = wether or not to add \n at end
- String readLine(char separator = '\n');
-};
-
-#endif
diff --git a/Source/Kernel/VFS/VFS.ns.cpp b/Source/Kernel/VFS/VFS.ns.cpp
index fdfc265..e95b911 100644
--- a/Source/Kernel/VFS/VFS.ns.cpp
+++ b/Source/Kernel/VFS/VFS.ns.cpp
@@ -39,7 +39,7 @@ FSNode* find(const String& path, FSNode* start) {
return node;
}
-FSNode* createFile(const String& path, FSNode* start) {
+FSNode* createFile(const String& path, FSNode* start, bool vrfyperm) {
if (find(path, start) != NULL) return NULL; //Something already has that name.
if (start == 0) start = rootNode;
@@ -65,13 +65,12 @@ FSNode* createFile(const String& path, FSNode* start) {
}
if (node->type() == NT_DIRECTORY) {
- return ((DirectoryNode*)node)->createFile(name);
- } else {
- return NULL;
+ if ((vrfyperm && node->writable()) or !vrfyperm) return ((DirectoryNode*)node)->createFile(name);
}
+ return NULL;
}
-FSNode* createDirectory(const String& path, FSNode* start) {
+FSNode* createDirectory(const String& path, FSNode* start, bool vrfyperm) {
if (find(path, start) != NULL) return NULL; //Something already has that name.
if (start == 0) start = rootNode;
@@ -97,40 +96,8 @@ FSNode* createDirectory(const String& path, FSNode* start) {
}
if (node->type() == NT_DIRECTORY) {
- return ((DirectoryNode*)node)->createDirectory(name);
- } else {
- return NULL;
+ if ((vrfyperm && node->writable()) or !vrfyperm) return ((DirectoryNode*)node)->createDirectory(name);
}
-}
-
-//Same as createDirectory but checks for parent directory permissions for current process
-FSNode* mkdir(const String& path, FSNode* start) {
- if (find(path, start) != NULL) return NULL; //Something already has that name.
- if (start == 0) start = rootNode;
-
- Vector<String> p = path.split("/");
- String name = p.back();
- p.pop();
-
- FSNode* node = start;
- if (!path.empty()) {
- if (p[0].empty()) node = rootNode;
- for (u32int i = 0; i < p.size(); i++) {
- if (p[i] == "..") {
- node = node->getParent();
- } else if (!p[i].empty() and p[i] != ".") {
- if (node->type() == NT_DIRECTORY) {
- node = ((DirectoryNode*)node)->getChild(p[i]);
- } else {
- node = NULL;
- }
- }
- if (node == NULL) return node;
- }
- }
-
- if (node->type() == NT_DIRECTORY)
- if (node->writable()) return ((DirectoryNode*)node)->createDirectory(name);
return NULL;
}
diff --git a/Source/Kernel/VFS/VFS.ns.h b/Source/Kernel/VFS/VFS.ns.h
index 63229bf..f1d628f 100644
--- a/Source/Kernel/VFS/VFS.ns.h
+++ b/Source/Kernel/VFS/VFS.ns.h
@@ -13,9 +13,8 @@ namespace VFS {
DirectoryNode* getRootNode();
FSNode* find(const String& path, FSNode* start = 0);
- FSNode* createFile(const String& path, FSNode* start = 0);
- FSNode* createDirectory(const String& path, FSNode* start = 0);
- FSNode* mkdir(const String& path, FSNode* start = 0); //Same as createDirectory, except it checks for parent directory writablilty by current process
+ FSNode* createFile(const String& path, FSNode* start = 0, bool vrfyperm = false);
+ FSNode* createDirectory(const String& path, FSNode* start = 0, bool vrfyperm = false);
bool remove(FSNode* node);
bool remove(const String& path, FSNode* start = 0); //Returns false for non-empty directories
String path(FSNode* node); //Returns complete path for a node