From 186eaef12ad34d922886f0944156c9cebf222884 Mon Sep 17 00:00:00 2001 From: Tomas 'ZeXx86' Jedrzejek Date: Fri, 16 Jan 2009 17:23:34 +0100 Subject: [PATCH] added znfs daemon - for znfs host side; touch.c was missing --- kernel/utils/fs/touch.c | 34 +++++++++++++ tools/znfsd/Makefile | 8 +++ tools/znfsd/client.c | 57 +++++++++++++++++++++ tools/znfsd/client.h | 39 ++++++++++++++ tools/znfsd/main.c | 38 ++++++++++++++ tools/znfsd/net.c | 109 ++++++++++++++++++++++++++++++++++++++++ tools/znfsd/proto.c | 131 ++++++++++++++++++++++++++++++++++++++++++++++++ 7 files changed, 416 insertions(+) create mode 100644 kernel/utils/fs/touch.c create mode 100644 tools/znfsd/Makefile create mode 100644 tools/znfsd/client.c create mode 100644 tools/znfsd/client.h create mode 100644 tools/znfsd/main.c create mode 100644 tools/znfsd/net.c create mode 100644 tools/znfsd/proto.c diff --git a/kernel/utils/fs/touch.c b/kernel/utils/fs/touch.c new file mode 100644 index 0000000..15f7b87 --- /dev/null +++ b/kernel/utils/fs/touch.c @@ -0,0 +1,34 @@ +/* + * ZeX/OS + * Copyright (C) 2009 Tomas 'ZeXx86' Jedrzejek (zexx86@gmail.com) + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + + +#include +#include +#include +#include + +int touch (unsigned char *fi) +{ + unsigned fi_len = strlen (fi); + DPRINT ("fi: '%s' (%d)\n", fi, fi_len); + + if (!vfs_touch (fi, fi_len)) + printf("missing operand : %s\n", fi); + + return 1; +} diff --git a/tools/znfsd/Makefile b/tools/znfsd/Makefile new file mode 100644 index 0000000..53bca14 --- /dev/null +++ b/tools/znfsd/Makefile @@ -0,0 +1,8 @@ +CFLAGS= -O2 +CPP= gcc + +preklad: main.c + $(CPP) $(CFLAGS) -oznfsd main.c client.c proto.c net.c + +clean: + rm -f znfsd diff --git a/tools/znfsd/client.c b/tools/znfsd/client.c new file mode 100644 index 0000000..f1906b2 --- /dev/null +++ b/tools/znfsd/client.c @@ -0,0 +1,57 @@ +#include +#include +#include "client.h" + +client_t client_list; + +int client_send (client_t *c, char *data, unsigned len) +{ + return net_send (c->fd, data, len); +} + +int client_add (int fd) +{ + // alloc and init context + client_t *ctx = (client_t *) malloc (sizeof (client_t)); + + if (!ctx) + return 0; + + ctx->fd = fd; + ctx->state = CLIENT_STATE_CONNECTED; + + ctx->next = &client_list; + ctx->prev = client_list.prev; + ctx->prev->next = ctx; + ctx->next->prev = ctx; + + return 1; +} + +int client_handle (client_t *c, char *data, unsigned len) +{ + if (c->state == CLIENT_STATE_CONNECTED) { + data[len] = '\0'; + return proto_handle (c, data, len); + } else if (c->state == CLIENT_STATE_DISCONNECTED) { + /* disconnect socket */ + close (c->fd); + + /* delete client_t * struct from list */ + c->next->prev = c->prev; + c->prev->next = c->next; + + free (c); + return 0; + } + + return 1; +} + +int client_init () +{ + client_list.next = &client_list; + client_list.prev = &client_list; + + return 1; +} diff --git a/tools/znfsd/client.h b/tools/znfsd/client.h new file mode 100644 index 0000000..cdaed6e --- /dev/null +++ b/tools/znfsd/client.h @@ -0,0 +1,39 @@ +/* + * ZeX/OS + * Copyright (C) 2009 Tomas 'ZeXx86' Jedrzejek (zexx86@gmail.com) + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + + +#ifndef _CLIENT_H +#define _CLIENT_H + +#define CLIENT_STATE_CONNECTED 0x1 +#define CLIENT_STATE_DISCONNECTED 0x2 + +/* Client structure */ +typedef struct client_context { + struct client_context *next, *prev; + + int fd; + unsigned state; +} client_t; + +extern int client_send (client_t *c, char *data, unsigned len); +extern int client_add (int fd); +extern int client_handle (client_t *c, char *data, unsigned len); +extern int client_init (); + +#endif diff --git a/tools/znfsd/main.c b/tools/znfsd/main.c new file mode 100644 index 0000000..bad99c8 --- /dev/null +++ b/tools/znfsd/main.c @@ -0,0 +1,38 @@ +#include +#include +#include "client.h" + +int init () +{ + if (!net_init ()) + return 0; + + if (!client_init ()) + return 0; + + chroot ("root"); + + return 1; +} + +int loop () +{ + int ret = 1; + + while (ret) + ret = net_loop (); +} + +int main (int argc, char **argv) +{ + printf ("ZeX/OS Network FileSystem Daemon\n"); + + if (!init ()) { + printf ("> ERROR -> !init ()\n"); + return -1; + } + + loop (); + + return 0; +} diff --git a/tools/znfsd/net.c b/tools/znfsd/net.c new file mode 100644 index 0000000..c4e55dc --- /dev/null +++ b/tools/znfsd/net.c @@ -0,0 +1,109 @@ +#include +#include +#include +#include +#include +#include +#include "client.h" + +int mainsocket; +struct sockaddr_in sockserver; +struct sockaddr_in sockclient; +socklen_t addrlen; +char buffer[1530]; + +extern client_t client_list; + +int net_send (int fd, char *str, unsigned len) +{ + int oldFlag = fcntl (fd, F_GETFL, 0); + if (fcntl (fd, F_SETFL, oldFlag & ~O_NONBLOCK) == -1) { + printf ("Cant set socket to blocking mode\n"); + return 0; + } + + int ret = send (fd, str, len, 0); + + oldFlag = fcntl (fd, F_GETFL, 0); + if (fcntl (fd, F_SETFL, oldFlag | O_NONBLOCK) == -1) { + printf ("Cant set socket to nonblocking mode\n"); + return 0; + } + + return ret; +} + +int net_accept () +{ + int newfd = accept (mainsocket, (struct sockaddr *) &sockclient, &addrlen); + + if (newfd > 0) { + printf ("> New client connected fd (%d) - %s\n", newfd, inet_ntoa (sockclient.sin_addr)); + + client_add (newfd); + + return newfd; + } + + return 0; +} + +int net_loop () +{ + net_accept (); + + client_t *c; + for (c = client_list.next; c != &client_list; c = c->next) { + if (!c) + continue; + + int ret = recv (c->fd, buffer, 1500, 0); + + if (ret > 0) + if (!client_handle (c, buffer, ret)) + break; + } + + return 1; +} + +int net_init () +{ + int port = 5333; + + if ((mainsocket = socket (AF_INET, SOCK_STREAM, IPPROTO_TCP)) == -1) { + printf ("Cant create socket\n"); + return -1; + } + + // 1) Family of protocols + sockserver.sin_family = AF_INET; + // 2) Set number of listen port + sockserver.sin_port = htons (port); + // 3) Listen IP address + sockserver.sin_addr.s_addr = INADDR_ANY; + + unsigned long yes = 1; + setsockopt (mainsocket, SOL_SOCKET, SO_REUSEADDR, (char *) &yes, sizeof (yes)); + + // Bind on our socket + if (bind (mainsocket, (struct sockaddr *) &sockserver, sizeof (sockserver)) == -1) { + printf ("bind () - port is used\n"); + return -1; + } + + // Create queue for accept + if (listen (mainsocket, 10) == -1) { + printf ("ERROR -> listen () == -1\n"); + return -1; + } + + // set mainSocket to non-blocking mode + int oldFlag = fcntl (mainsocket, F_GETFL, 0); + if (fcntl (mainsocket, F_SETFL, oldFlag | O_NONBLOCK) == -1) { + printf ("Cant set socket to nonblocking mode\n"); + return 0; + } + + return 1; +} diff --git a/tools/znfsd/proto.c b/tools/znfsd/proto.c new file mode 100644 index 0000000..9c8812e --- /dev/null +++ b/tools/znfsd/proto.c @@ -0,0 +1,131 @@ +#include +#include +#include +#include +#include +#include "client.h" + +#define PROTO_MKDIR 0x1 +#define PROTO_RMDIR 0x2 +#define PROTO_CREAT 0x3 +#define PROTO_RM 0x4 +#define PROTO_CHDIR 0x5 +#define PROTO_READ 0x6 + +int proto_handle (client_t *c, char *data, unsigned len) +{ + char name[256]; + unsigned char l = 0; + int r = -1; + + printf ("proto_handle () - '%s' : %d\n", data, len); + + switch (data[0]) { + case PROTO_MKDIR: + if (len < 3) + return 0; + + l = data[1]; + + if (l > len-2) + return 0; + + memcpy (name, data+2, l); + name[l] = '\0'; + + r = mkdir (name, 0777); + + printf ("mkdir (%s, %x) = %d\n", name, 0x0777, r); + break; + case PROTO_RMDIR: + if (len < 3) + return 0; + + l = data[1]; + + if (l > len-2) + return 0; + + memcpy (name, data+2, l); + name[l] = '\0'; + + r = rmdir (name); + + printf ("rmdir (%s) = %d\n", name, r); + break; + case PROTO_CREAT: + if (len < 3) + return 0; + + l = data[1]; + + if (l > len-2) + return 0; + + memcpy (name, data+2, l); + name[l] = '\0'; + + r = creat (name, 0777); + + printf ("creat (%s, %x) = %d\n", name, 0x0777, r); + break; + case PROTO_RM: + + printf ("rm (%s) = %d\n", "", r); + break; + case PROTO_CHDIR: + if (len < 3) + return 0; + + l = data[1]; + + if (l > len-2) + return 0; + + memcpy (name, data+2, l); + name[l] = '\0'; + + r = chdir (name); + + printf ("chdir (%s) = %d\n", name, r); + break; + case PROTO_READ: + if (len < 3) + return 0; + + l = data[1]; + + if (l > len-2) + return 0; + + memcpy (name, data+2, l); + name[l] = '\0'; + + FILE *fr; + char s[1024]; + + fr = fopen (name, "r"); + + if (!fr) { + goto done; + } + + while (fgets (s, sizeof (s), fr) != NULL) { + client_send (c, s, 1024); + usleep (10); + } + + fclose (fr); + + unsigned p = 0xf9da1e9; // some kind of magic .. eh it is match for EOF + client_send (c, (char *) &p, 4); + + r = 0; + +done: + printf ("read (%s) = %d\n", name, r); + break; + } + + return 1; +} -- 2.11.4.GIT