1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #ifndef LIBRARIES_NACL_IO_KERNEL_PROXY_H_
6 #define LIBRARIES_NACL_IO_KERNEL_PROXY_H_
11 #include "nacl_io/event_emitter.h"
12 #include "nacl_io/host_resolver.h"
13 #include "nacl_io/kernel_object.h"
14 #include "nacl_io/mount_factory.h"
15 #include "nacl_io/mount_stream.h"
16 #include "nacl_io/ossignal.h"
17 #include "nacl_io/ossocket.h"
18 #include "nacl_io/ostypes.h"
19 #include "nacl_io/osutime.h"
25 class PepperInterface;
28 // KernelProxy provide one-to-one mapping for libc kernel calls. Calls to the
29 // proxy will result in IO access to the provided Mount and MountNode objects.
31 // NOTE: The KernelProxy does not directly take any kernel locks, all locking
32 // is done by the parent class KernelObject. Instead, KernelProxy is
33 // responsible for taking the locks of the KernelHandle, and MountNode objects.
34 // For this reason, a KernelObject call should not be done while holding
35 // a handle or node lock. In addition, to ensure locking order,
36 // a KernelHandle lock must never be taken after taking the associated
39 // NOTE: The KernelProxy is the only class that should be setting errno. All
40 // other classes should return Error (as defined by nacl_io/error.h).
41 class KernelProxy : protected KernelObject {
43 typedef std::map<std::string, MountFactory*> MountFactoryMap_t;
46 virtual ~KernelProxy();
48 // Takes ownership of |ppapi|.
49 // |ppapi| may be NULL. If so, no mount that uses pepper calls can be mounted.
50 virtual Error Init(PepperInterface* ppapi);
52 virtual int pipe(int pipefds[2]);
54 // NaCl-only function to read resources specified in the NMF file.
55 virtual int open_resource(const char* file);
57 // KernelHandle and FD allocation and manipulation functions.
58 virtual int open(const char* path, int open_flags);
59 virtual int close(int fd);
60 virtual int dup(int fd);
61 virtual int dup2(int fd, int newfd);
63 // Path related System calls handled by KernelProxy (not mount-specific)
64 virtual int chdir(const char* path);
65 virtual char* getcwd(char* buf, size_t size);
66 virtual char* getwd(char* buf);
67 virtual int mount(const char *source,
69 const char *filesystemtype,
70 unsigned long mountflags,
72 virtual int umount(const char *path);
74 // Stub system calls that don't do anything (yet), handled by KernelProxy.
75 virtual int chown(const char* path, uid_t owner, gid_t group);
76 virtual int fchown(int fd, uid_t owner, gid_t group);
77 virtual int lchown(const char* path, uid_t owner, gid_t group);
78 virtual int utime(const char* filename, const struct utimbuf* times);
80 // System calls that take a path as an argument:
81 // The kernel proxy will look for the Node associated to the path. To
82 // find the node, the kernel proxy calls the corresponding mount's GetNode()
83 // method. The corresponding method will be called. If the node
84 // cannot be found, errno is set and -1 is returned.
85 virtual int chmod(const char *path, mode_t mode);
86 virtual int mkdir(const char *path, mode_t mode);
87 virtual int rmdir(const char *path);
88 virtual int stat(const char *path, struct stat *buf);
90 // System calls that take a file descriptor as an argument:
91 // The kernel proxy will determine to which mount the file
92 // descriptor's corresponding file handle belongs. The
93 // associated mount's function will be called.
94 virtual ssize_t read(int fd, void *buf, size_t nbyte);
95 virtual ssize_t write(int fd, const void *buf, size_t nbyte);
97 virtual int fchmod(int fd, int prot);
98 virtual int fcntl(int fd, int request, va_list args);
99 virtual int fstat(int fd, struct stat *buf);
100 virtual int getdents(int fd, void *buf, unsigned int count);
101 virtual int fchdir(int fd);
102 virtual int ftruncate(int fd, off_t length);
103 virtual int fsync(int fd);
104 virtual int fdatasync(int fd);
105 virtual int isatty(int fd);
106 virtual int ioctl(int fd, int request, va_list args);
108 // lseek() relies on the mount's Stat() to determine whether or not the
109 // file handle corresponding to fd is a directory
110 virtual off_t lseek(int fd, off_t offset, int whence);
112 // remove() uses the mount's GetNode() and Stat() to determine whether or
113 // not the path corresponds to a directory or a file. The mount's Rmdir()
114 // or Unlink() is called accordingly.
115 virtual int remove(const char* path);
116 // unlink() is a simple wrapper around the mount's Unlink function.
117 virtual int unlink(const char* path);
118 virtual int truncate(const char* path, off_t len);
119 virtual int lstat(const char* path, struct stat* buf);
120 virtual int rename(const char* path, const char* newpath);
121 // access() uses the Mount's Stat().
122 virtual int access(const char* path, int amode);
123 virtual int readlink(const char *path, char *buf, size_t count);
124 virtual int utimes(const char *filename, const struct timeval times[2]);
126 virtual int link(const char* oldpath, const char* newpath);
127 virtual int symlink(const char* oldpath, const char* newpath);
129 virtual void* mmap(void* addr,
135 virtual int munmap(void* addr, size_t length);
136 virtual int tcflush(int fd, int queue_selector);
137 virtual int tcgetattr(int fd, struct termios* termios_p);
138 virtual int tcsetattr(int fd, int optional_actions,
139 const struct termios *termios_p);
141 virtual int kill(pid_t pid, int sig);
142 virtual sighandler_t sigset(int signum, sighandler_t handler);
144 #ifdef PROVIDES_SOCKET_API
145 virtual int select(int nfds, fd_set* readfds, fd_set* writefds,
146 fd_set* exceptfds, struct timeval* timeout);
148 virtual int poll(struct pollfd *fds, nfds_t nfds, int timeout);
150 // Socket support functions
151 virtual int accept(int fd, struct sockaddr* addr, socklen_t* len);
152 virtual int bind(int fd, const struct sockaddr* addr, socklen_t len);
153 virtual int connect(int fd, const struct sockaddr* addr, socklen_t len);
154 virtual struct hostent* gethostbyname(const char* name);
155 virtual int getpeername(int fd, struct sockaddr* addr, socklen_t* len);
156 virtual int getsockname(int fd, struct sockaddr* addr, socklen_t* len);
157 virtual int getsockopt(int fd,
162 virtual int listen(int fd, int backlog);
163 virtual ssize_t recv(int fd,
167 virtual ssize_t recvfrom(int fd,
171 struct sockaddr* addr,
173 virtual ssize_t recvmsg(int fd, struct msghdr* msg, int flags);
174 virtual ssize_t send(int fd, const void* buf, size_t len, int flags);
175 virtual ssize_t sendto(int fd,
179 const struct sockaddr* addr,
181 virtual ssize_t sendmsg(int fd, const struct msghdr* msg, int flags);
182 virtual int setsockopt(int fd,
187 virtual int shutdown(int fd, int how);
188 virtual int socket(int domain, int type, int protocol);
189 virtual int socketpair(int domain, int type, int protocol, int* sv);
190 #endif // PROVIDES_SOCKET_API
193 MountFactoryMap_t factories_;
194 sdk_util::ScopedRef<MountStream> stream_mount_;
196 PepperInterface* ppapi_;
197 static KernelProxy *s_instance_;
198 sighandler_t sigwinch_handler_;
199 #ifdef PROVIDES_SOCKET_API
200 HostResolver host_resolver_;
203 #ifdef PROVIDES_SOCKET_API
204 virtual int AcquireSocketHandle(int fd, ScopedKernelHandle* handle);
207 ScopedEventEmitter signal_emitter_;
208 DISALLOW_COPY_AND_ASSIGN(KernelProxy);
211 } // namespace nacl_io
213 #endif // LIBRARIES_NACL_IO_KERNEL_PROXY_H_