1 //===-- stubs.c -----------------------------------------------------------===//
2 //
3 //                     The KLEE Symbolic Virtual Machine
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 
10 #ifdef __FreeBSD__
11 #include "FreeBSD.h"
12 #endif
13 #include <errno.h>
14 #include <limits.h>
15 #include <signal.h>
16 #include <stdio.h>
17 #include <stdlib.h>
18 #include <string.h>
19 #include <time.h>
20 #include <unistd.h>
21 #include <utime.h>
22 #ifndef __FreeBSD__
23 #include <utmp.h>
24 #endif
25 #include <sys/mman.h>
26 #include <sys/resource.h>
27 #include <sys/stat.h>
28 #include <sys/time.h>
29 #include <sys/times.h>
30 #include <sys/types.h>
31 #include <sys/wait.h>
32 
33 #include "klee/Config/config.h"
34 
35 void klee_warning(const char*);
36 void klee_warning_once(const char*);
37 
38 /* Silent ignore */
39 
40 int __syscall_rt_sigaction(int signum, const struct sigaction *act,
41                            struct sigaction *oldact, size_t _something)
42      __attribute__((weak));
43 
__syscall_rt_sigaction(int signum,const struct sigaction * act,struct sigaction * oldact,size_t _something)44 int __syscall_rt_sigaction(int signum, const struct sigaction *act,
45                            struct sigaction *oldact, size_t _something) {
46   klee_warning_once("silently ignoring");
47   return 0;
48 }
49 
50 int sigaction(int signum, const struct sigaction *act,
51               struct sigaction *oldact) __attribute__((weak));
52 
sigaction(int signum,const struct sigaction * act,struct sigaction * oldact)53 int sigaction(int signum, const struct sigaction *act,
54               struct sigaction *oldact) {
55   klee_warning_once("silently ignoring");
56   return 0;
57 }
58 
59 int sigprocmask(int how, const sigset_t *set, sigset_t *oldset)
60      __attribute__((weak));
sigprocmask(int how,const sigset_t * set,sigset_t * oldset)61 int sigprocmask(int how, const sigset_t *set, sigset_t *oldset) {
62   klee_warning_once("silently ignoring");
63   return 0;
64 }
65 
66 /* Not even worth warning about these */
67 int fdatasync(int fd) __attribute__((weak));
fdatasync(int fd)68 int fdatasync(int fd) {
69   return 0;
70 }
71 
72 /* Not even worth warning about this */
73 void sync(void) __attribute__((weak));
sync(void)74 void sync(void) {
75 }
76 
77 /* Error ignore */
78 
79 extern int __fgetc_unlocked(FILE *f);
80 extern int __fputc_unlocked(int c, FILE *f);
81 
82 int __socketcall(int type, int *args) __attribute__((weak));
__socketcall(int type,int * args)83 int __socketcall(int type, int *args) {
84   klee_warning("ignoring (EAFNOSUPPORT)");
85   errno = EAFNOSUPPORT;
86   return -1;
87 }
88 
89 int _IO_getc(FILE *f) __attribute__((weak));
_IO_getc(FILE * f)90 int _IO_getc(FILE *f) {
91   return __fgetc_unlocked(f);
92 }
93 
94 int _IO_putc(int c, FILE *f) __attribute__((weak));
_IO_putc(int c,FILE * f)95 int _IO_putc(int c, FILE *f) {
96   return __fputc_unlocked(c, f);
97 }
98 
99 int mkdir(const char *pathname, mode_t mode) __attribute__((weak));
mkdir(const char * pathname,mode_t mode)100 int mkdir(const char *pathname, mode_t mode) {
101   klee_warning("ignoring (EIO)");
102   errno = EIO;
103   return -1;
104 }
105 
106 int mkfifo(const char *pathname, mode_t mode) __attribute__((weak));
mkfifo(const char * pathname,mode_t mode)107 int mkfifo(const char *pathname, mode_t mode) {
108   klee_warning("ignoring (EIO)");
109   errno = EIO;
110   return -1;
111 }
112 
113 int mknod(const char *pathname, mode_t mode, dev_t dev) __attribute__((weak));
mknod(const char * pathname,mode_t mode,dev_t dev)114 int mknod(const char *pathname, mode_t mode, dev_t dev) {
115   klee_warning("ignoring (EIO)");
116   errno = EIO;
117   return -1;
118 }
119 
120 int pipe(int filedes[2]) __attribute__((weak));
pipe(int filedes[2])121 int pipe(int filedes[2]) {
122   klee_warning("ignoring (ENFILE)");
123   errno = ENFILE;
124   return -1;
125 }
126 
127 int link(const char *oldpath, const char *newpath) __attribute__((weak));
link(const char * oldpath,const char * newpath)128 int link(const char *oldpath, const char *newpath) {
129   klee_warning("ignoring (EPERM)");
130   errno = EPERM;
131   return -1;
132 }
133 
134 int symlink(const char *oldpath, const char *newpath) __attribute__((weak));
symlink(const char * oldpath,const char * newpath)135 int symlink(const char *oldpath, const char *newpath) {
136   klee_warning("ignoring (EPERM)");
137   errno = EPERM;
138   return -1;
139 }
140 
141 int rename(const char *oldpath, const char *newpath) __attribute__((weak));
rename(const char * oldpath,const char * newpath)142 int rename(const char *oldpath, const char *newpath) {
143   klee_warning("ignoring (EPERM)");
144   errno = EPERM;
145   return -1;
146 }
147 
148 int nanosleep(const struct timespec *req, struct timespec *rem) __attribute__((weak));
nanosleep(const struct timespec * req,struct timespec * rem)149 int nanosleep(const struct timespec *req, struct timespec *rem) {
150   return 0;
151 }
152 
153 /* XXX why can't I call this internally? */
154 int clock_gettime(clockid_t clk_id, struct timespec *res) __attribute__((weak));
clock_gettime(clockid_t clk_id,struct timespec * res)155 int clock_gettime(clockid_t clk_id, struct timespec *res) {
156   /* Fake */
157   struct timeval tv;
158   gettimeofday(&tv, NULL);
159   res->tv_sec = tv.tv_sec;
160   res->tv_nsec = tv.tv_usec * 1000;
161   return 0;
162 }
163 
164 int clock_settime(clockid_t clk_id, const struct timespec *res) __attribute__((weak));
clock_settime(clockid_t clk_id,const struct timespec * res)165 int clock_settime(clockid_t clk_id, const struct timespec *res) {
166   klee_warning("ignoring (EPERM)");
167   errno = EPERM;
168   return -1;
169 }
170 
time(time_t * t)171 time_t time(time_t *t) {
172   struct timeval tv;
173   gettimeofday(&tv, NULL);
174   if (t)
175     *t = tv.tv_sec;
176   return tv.tv_sec;
177 }
178 
times(struct tms * buf)179 clock_t times(struct tms *buf) {
180   /* Fake */
181   if (!buf)
182     klee_warning("returning 0\n");
183   else {
184     klee_warning("setting all times to 0 and returning 0\n");
185     buf->tms_utime = 0;
186     buf->tms_stime = 0;
187     buf->tms_cutime = 0;
188     buf->tms_cstime = 0;
189   }
190   return 0;
191 }
192 
193 #ifndef __FreeBSD__
194 struct utmpx *getutxent(void) __attribute__((weak));
getutxent(void)195 struct utmpx *getutxent(void) {
196   return (struct utmpx*) getutent();
197 }
198 
199 void setutxent(void) __attribute__((weak));
setutxent(void)200 void setutxent(void) {
201   setutent();
202 }
203 
204 void endutxent(void) __attribute__((weak));
endutxent(void)205 void endutxent(void) {
206   endutent();
207 }
208 
209 int utmpxname(const char *file) __attribute__((weak));
utmpxname(const char * file)210 int utmpxname(const char *file) {
211   utmpname(file);
212   return 0;
213 }
214 #endif
215 
216 int euidaccess(const char *pathname, int mode) __attribute__((weak));
euidaccess(const char * pathname,int mode)217 int euidaccess(const char *pathname, int mode) {
218   return access(pathname, mode);
219 }
220 
221 int eaccess(const char *pathname, int mode) __attribute__((weak));
eaccess(const char * pathname,int mode)222 int eaccess(const char *pathname, int mode) {
223   return euidaccess(pathname, mode);
224 }
225 
226 int group_member (gid_t __gid) __attribute__((weak));
group_member(gid_t __gid)227 int group_member (gid_t __gid) {
228   return ((__gid == getgid ()) || (__gid == getegid ()));
229 }
230 
231 int utime(const char *filename, const struct utimbuf *buf) __attribute__((weak));
utime(const char * filename,const struct utimbuf * buf)232 int utime(const char *filename, const struct utimbuf *buf) {
233   klee_warning("ignoring (EPERM)");
234   errno = EPERM;
235   return -1;
236 }
237 
238 int futimes(int fd, const struct timeval times[2]) __attribute__((weak));
futimes(int fd,const struct timeval times[2])239 int futimes(int fd, const struct timeval times[2]) {
240   klee_warning("ignoring (EBADF)");
241   errno = EBADF;
242   return -1;
243 }
244 
strverscmp(__const char * __s1,__const char * __s2)245 int strverscmp (__const char *__s1, __const char *__s2) {
246   return strcmp(__s1, __s2); /* XXX no doubt this is bad */
247 }
248 
249 #if __GLIBC_PREREQ(2, 25)
250 #define gnu_dev_type	dev_t
251 #else
252 #define gnu_dev_type	unsigned long long int
253 #endif
254 
255 unsigned int gnu_dev_major(gnu_dev_type __dev) __attribute__((weak));
gnu_dev_major(gnu_dev_type __dev)256 unsigned int gnu_dev_major(gnu_dev_type __dev) {
257   return ((__dev >> 8) & 0xfff) | ((unsigned int) (__dev >> 32) & ~0xfff);
258 }
259 
260 unsigned int gnu_dev_minor(gnu_dev_type __dev) __attribute__((weak));
gnu_dev_minor(gnu_dev_type __dev)261 unsigned int gnu_dev_minor(gnu_dev_type __dev) {
262   return (__dev & 0xff) | ((unsigned int) (__dev >> 12) & ~0xff);
263 }
264 
265 gnu_dev_type gnu_dev_makedev(unsigned int __major, unsigned int __minor) __attribute__((weak));
gnu_dev_makedev(unsigned int __major,unsigned int __minor)266 gnu_dev_type gnu_dev_makedev(unsigned int __major, unsigned int __minor) {
267   return ((__minor & 0xff) | ((__major & 0xfff) << 8)
268           | (((gnu_dev_type) (__minor & ~0xff)) << 12)
269           | (((gnu_dev_type) (__major & ~0xfff)) << 32));
270 }
271 
272 char *canonicalize_file_name (const char *name) __attribute__((weak));
canonicalize_file_name(const char * name)273 char *canonicalize_file_name (const char *name) {
274   // Although many C libraries allocate resolved_name in realpath() if it is NULL,
275   // this behaviour is implementation-defined (POSIX) and not implemented in uclibc.
276   char * resolved_name = malloc(PATH_MAX);
277   if (!resolved_name) return NULL;
278   if (!realpath(name, resolved_name)) {
279     free(resolved_name);
280     return NULL;
281   }
282   return resolved_name;
283 }
284 
285 int getloadavg(double loadavg[], int nelem) __attribute__((weak));
getloadavg(double loadavg[],int nelem)286 int getloadavg(double loadavg[], int nelem) {
287   klee_warning("ignoring (-1 result)");
288   return -1;
289 }
290 
291 pid_t wait(int *status) __attribute__((weak));
wait(int * status)292 pid_t wait(int *status) {
293   klee_warning("ignoring (ECHILD)");
294   errno = ECHILD;
295   return -1;
296 }
297 
298 pid_t wait3(int *status, int options, struct rusage *rusage) __attribute__((weak));
wait3(int * status,int options,struct rusage * rusage)299 pid_t wait3(int *status, int options, struct rusage *rusage) {
300   klee_warning("ignoring (ECHILD)");
301   errno = ECHILD;
302   return -1;
303 }
304 
305 pid_t wait4(pid_t pid, int *status, int options, struct rusage *rusage) __attribute__((weak));
wait4(pid_t pid,int * status,int options,struct rusage * rusage)306 pid_t wait4(pid_t pid, int *status, int options, struct rusage *rusage) {
307   klee_warning("ignoring (ECHILD)");
308   errno = ECHILD;
309   return -1;
310 }
311 
312 pid_t waitpid(pid_t pid, int *status, int options) __attribute__((weak));
waitpid(pid_t pid,int * status,int options)313 pid_t waitpid(pid_t pid, int *status, int options) {
314   klee_warning("ignoring (ECHILD)");
315   errno = ECHILD;
316   return -1;
317 }
318 
319 pid_t waitid(idtype_t idtype, id_t id, siginfo_t *infop, int options) __attribute__((weak));
waitid(idtype_t idtype,id_t id,siginfo_t * infop,int options)320 pid_t waitid(idtype_t idtype, id_t id, siginfo_t *infop, int options) {
321   klee_warning("ignoring (ECHILD)");
322   errno = ECHILD;
323   return -1;
324 }
325 
326 /* ACL */
327 
328 /* FIXME: We need autoconf magic for this. */
329 
330 #ifdef HAVE_SYS_ACL_H
331 
332 #include <sys/acl.h>
333 
334 int acl_delete_def_file(const char *path_p) __attribute__((weak));
acl_delete_def_file(const char * path_p)335 int acl_delete_def_file(const char *path_p) {
336   klee_warning("ignoring (EPERM)");
337   errno = EPERM;
338   return -1;
339 }
340 
341 int acl_extended_file(const char path_p) __attribute__((weak));
acl_extended_file(const char path_p)342 int acl_extended_file(const char path_p) {
343   klee_warning("ignoring (ENOENT)");
344   errno = ENOENT;
345   return -1;
346 }
347 
348 int acl_entries(acl_t acl) __attribute__((weak));
acl_entries(acl_t acl)349 int acl_entries(acl_t acl) {
350   klee_warning("ignoring (EINVAL)");
351   errno = EINVAL;
352   return -1;
353 }
354 
355 acl_t acl_from_mode(mode_t mode) __attribute__((weak));
acl_from_mode(mode_t mode)356 acl_t acl_from_mode(mode_t mode) {
357   klee_warning("ignoring (ENOMEM)");
358   errno = ENOMEM;
359   return NULL;
360 }
361 
362 acl_t acl_get_fd(int fd) __attribute__((weak));
acl_get_fd(int fd)363 acl_t acl_get_fd(int fd) {
364   klee_warning("ignoring (ENOMEM)");
365   errno = ENOMEM;
366   return NULL;
367 }
368 
369 acl_t acl_get_file(const char *pathname, acl_type_t type) __attribute__((weak));
acl_get_file(const char * pathname,acl_type_t type)370 acl_t acl_get_file(const char *pathname, acl_type_t type) {
371   klee_warning("ignoring (ENONMEM)");
372   errno = ENOMEM;
373   return NULL;
374 }
375 
376 int acl_set_fd(int fd, acl_t acl) __attribute__((weak));
acl_set_fd(int fd,acl_t acl)377 int acl_set_fd(int fd, acl_t acl) {
378   klee_warning("ignoring (EPERM)");
379   errno = EPERM;
380   return -1;
381 }
382 
383 int acl_set_file(const char *path_p, acl_type_t type, acl_t acl) __attribute__((weak));
acl_set_file(const char * path_p,acl_type_t type,acl_t acl)384 int acl_set_file(const char *path_p, acl_type_t type, acl_t acl) {
385   klee_warning("ignoring (EPERM)");
386   errno = EPERM;
387   return -1;
388 }
389 
390 int acl_free(void *obj_p) __attribute__((weak));
acl_free(void * obj_p)391 int acl_free(void *obj_p) {
392   klee_warning("ignoring (EINVAL)");
393   errno = EINVAL;
394   return -1;
395 }
396 
397 #endif
398 
399 int mount(const char *source, const char *target, const char *filesystemtype, unsigned long mountflags, const void *data) __attribute__((weak));
mount(const char * source,const char * target,const char * filesystemtype,unsigned long mountflags,const void * data)400 int mount(const char *source, const char *target, const char *filesystemtype, unsigned long mountflags, const void *data) {
401   klee_warning("ignoring (EPERM)");
402   errno = EPERM;
403   return -1;
404 }
405 
406 int umount(const char *target) __attribute__((weak));
umount(const char * target)407 int umount(const char *target) {
408   klee_warning("ignoring (EPERM)");
409   errno = EPERM;
410   return -1;
411 }
412 
413 int umount2(const char *target, int flags) __attribute__((weak));
umount2(const char * target,int flags)414 int umount2(const char *target, int flags) {
415   klee_warning("ignoring (EPERM)");
416   errno = EPERM;
417   return -1;
418 }
419 
420 #ifndef __FreeBSD__
421 int swapon(const char *path, int swapflags) __attribute__((weak));
swapon(const char * path,int swapflags)422 int swapon(const char *path, int swapflags) {
423 #else
424 int swapon(const char *path)__attribute__((weak));
425 int swapon(const char *path)
426 {
427 #endif
428   klee_warning("ignoring (EPERM)");
429   errno = EPERM;
430   return -1;
431 }
432 
433 int swapoff(const char *path) __attribute__((weak));
434 int swapoff(const char *path) {
435   klee_warning("ignoring (EPERM)");
436   errno = EPERM;
437   return -1;
438 }
439 
440 int setgid(gid_t gid) __attribute__((weak));
441 int setgid(gid_t gid) {
442   klee_warning("silently ignoring (returning 0)");
443   return 0;
444 }
445 
446 #ifndef __FreeBSD__
447 int setgroups(size_t size, const gid_t *list) __attribute__((weak));
448 int setgroups(size_t size, const gid_t *list) {
449 #else
450 int setgroups(int size, const gid_t *list) __attribute__((weak));
451 int setgroups(int size, const gid_t *list) {
452 #endif
453   klee_warning("ignoring (EPERM)");
454   errno = EPERM;
455   return -1;
456 }
457 
458 #ifndef __FreeBSD__
459 int sethostname(const char *name, size_t len) __attribute__((weak));
460 int sethostname(const char *name, size_t len) {
461 #else
462 int sethostname(const char *name, int len) __attribute__((weak));
463 int sethostname(const char *name, int len) {
464 #endif
465   klee_warning("ignoring (EPERM)");
466   errno = EPERM;
467   return -1;
468 }
469 
470 int setpgid(pid_t pid, pid_t pgid) __attribute__((weak));
471 int setpgid(pid_t pid, pid_t pgid) {
472   klee_warning("ignoring (EPERM)");
473   errno = EPERM;
474   return -1;
475 }
476 
477 #ifndef __FreeBSD__
478 int setpgrp(void) __attribute__((weak));
479 int setpgrp(void) {
480 #else
481 int setpgrp(pid_t a, pid_t b) __attribute__((weak));
482 int setpgrp(pid_t a, pid_t b) {
483 #endif
484   klee_warning("ignoring (EPERM)");
485   errno = EPERM;
486   return -1;
487 }
488 
489 #ifndef __FreeBSD__
490 int setpriority(__priority_which_t which, id_t who, int prio) __attribute__((weak));
491 int setpriority(__priority_which_t which, id_t who, int prio) {
492 #else
493 int setpriority(int which, int who, int prio) __attribute__((weak));
494 int setpriority(int which, int who, int prio) {
495 #endif
496   klee_warning("ignoring (EPERM)");
497   errno = EPERM;
498   return -1;
499 }
500 
501 int setresgid(gid_t rgid, gid_t egid, gid_t sgid) __attribute__((weak));
502 int setresgid(gid_t rgid, gid_t egid, gid_t sgid) {
503   klee_warning("ignoring (EPERM)");
504   errno = EPERM;
505   return -1;
506 }
507 
508 int setresuid(uid_t ruid, uid_t euid, uid_t suid) __attribute__((weak));
509 int setresuid(uid_t ruid, uid_t euid, uid_t suid) {
510   klee_warning("ignoring (EPERM)");
511   errno = EPERM;
512   return -1;
513 }
514 
515 #ifndef __FreeBSD__
516 int setrlimit(__rlimit_resource_t resource, const struct rlimit *rlim) __attribute__((weak));
517 int setrlimit(__rlimit_resource_t resource, const struct rlimit *rlim) {
518 #else
519 int setrlimit(int resource, const struct rlimit *rlp) __attribute__((weak));
520 int setrlimit(int resource, const struct rlimit *rlp) {
521 #endif
522   klee_warning("ignoring (EPERM)");
523   errno = EPERM;
524   return -1;
525 }
526 
527 #ifndef __FreeBSD__
528 int setrlimit64(__rlimit_resource_t resource, const struct rlimit64 *rlim) __attribute__((weak));
529 int setrlimit64(__rlimit_resource_t resource, const struct rlimit64 *rlim) {
530   klee_warning("ignoring (EPERM)");
531   errno = EPERM;
532   return -1;
533 }
534 #endif
535 
536 pid_t setsid(void) __attribute__((weak));
537 pid_t setsid(void) {
538   klee_warning("ignoring (EPERM)");
539   errno = EPERM;
540   return -1;
541 }
542 
543 int settimeofday(const struct timeval *tv, const struct timezone *tz) __attribute__((weak));
544 int settimeofday(const struct timeval *tv, const struct timezone *tz) {
545   klee_warning("ignoring (EPERM)");
546   errno = EPERM;
547   return -1;
548 }
549 
550 int setuid(uid_t uid) __attribute__((weak));
551 int setuid(uid_t uid) {
552   klee_warning("silently ignoring (returning 0)");
553   return 0;
554 }
555 
556 int reboot(int flag) __attribute__((weak));
557 int reboot(int flag) {
558   klee_warning("ignoring (EPERM)");
559   errno = EPERM;
560   return -1;
561 }
562 
563 int mlock(const void *addr, size_t len) __attribute__((weak));
564 int mlock(const void *addr, size_t len) {
565   klee_warning("ignoring (EPERM)");
566   errno = EPERM;
567   return -1;
568 }
569 
570 int munlock(const void *addr, size_t len) __attribute__((weak));
571 int munlock(const void *addr, size_t len) {
572   klee_warning("ignoring (EPERM)");
573   errno = EPERM;
574   return -1;
575 }
576 
577 int pause(void) __attribute__((weak));
578 int pause(void) {
579   klee_warning("ignoring (EPERM)");
580   errno = EPERM;
581   return -1;
582 }
583 
584 ssize_t readahead(int fd, off64_t *offset, size_t count) __attribute__((weak));
585 ssize_t readahead(int fd, off64_t *offset, size_t count) {
586   klee_warning("ignoring (EPERM)");
587   errno = EPERM;
588   return -1;
589 }
590 
591 void *mmap(void *start, size_t length, int prot, int flags, int fd, off_t offset) __attribute__((weak));
592 void *mmap(void *start, size_t length, int prot, int flags, int fd, off_t offset) {
593   klee_warning("ignoring (EPERM)");
594   errno = EPERM;
595   return (void*) -1;
596 }
597 
598 void *mmap64(void *start, size_t length, int prot, int flags, int fd, off64_t offset) __attribute__((weak));
599 void *mmap64(void *start, size_t length, int prot, int flags, int fd, off64_t offset) {
600   klee_warning("ignoring (EPERM)");
601   errno = EPERM;
602   return (void*) -1;
603 }
604 
605 int munmap(void*start, size_t length) __attribute__((weak));
606 int munmap(void*start, size_t length) {
607   klee_warning("ignoring (EPERM)");
608   errno = EPERM;
609   return -1;
610 }
611