1f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include <unistd.h>
2f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include <sys/types.h>
3f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include <fcntl.h>
4f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include <stdlib.h>
5f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include <stdio.h>
6f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include <errno.h>
7f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include <string.h>
8f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include <limits.h>
9f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include "selinux_internal.h"
10f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include "policy.h"
11f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include "mapping.h"
12f074036424618c130dacb3464465a8b40bffef5Stephen Smalley
13ab40ea9bfd71b50138f1482c4764a65ac17d8cafStephen Smalleyint security_compute_create(const char * scon,
14ab40ea9bfd71b50138f1482c4764a65ac17d8cafStephen Smalley				const char * tcon,
15f074036424618c130dacb3464465a8b40bffef5Stephen Smalley				security_class_t tclass,
16ab40ea9bfd71b50138f1482c4764a65ac17d8cafStephen Smalley				char ** newcon)
17f074036424618c130dacb3464465a8b40bffef5Stephen Smalley{
18f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	char path[PATH_MAX];
19f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	char *buf;
20f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	size_t size;
21f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	int fd, ret;
22f074036424618c130dacb3464465a8b40bffef5Stephen Smalley
23f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	if (!selinux_mnt) {
24f074036424618c130dacb3464465a8b40bffef5Stephen Smalley		errno = ENOENT;
25f074036424618c130dacb3464465a8b40bffef5Stephen Smalley		return -1;
26f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	}
27f074036424618c130dacb3464465a8b40bffef5Stephen Smalley
28f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	snprintf(path, sizeof path, "%s/create", selinux_mnt);
29f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	fd = open(path, O_RDWR);
30f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	if (fd < 0)
31f074036424618c130dacb3464465a8b40bffef5Stephen Smalley		return -1;
32f074036424618c130dacb3464465a8b40bffef5Stephen Smalley
33f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	size = selinux_page_size;
34f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	buf = malloc(size);
35f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	if (!buf) {
36f074036424618c130dacb3464465a8b40bffef5Stephen Smalley		ret = -1;
37f074036424618c130dacb3464465a8b40bffef5Stephen Smalley		goto out;
38f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	}
39f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	snprintf(buf, size, "%s %s %hu", scon, tcon, unmap_class(tclass));
40f074036424618c130dacb3464465a8b40bffef5Stephen Smalley
41f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	ret = write(fd, buf, strlen(buf));
42f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	if (ret < 0)
43f074036424618c130dacb3464465a8b40bffef5Stephen Smalley		goto out2;
44f074036424618c130dacb3464465a8b40bffef5Stephen Smalley
45f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	memset(buf, 0, size);
46f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	ret = read(fd, buf, size - 1);
47f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	if (ret < 0)
48f074036424618c130dacb3464465a8b40bffef5Stephen Smalley		goto out2;
49f074036424618c130dacb3464465a8b40bffef5Stephen Smalley
50f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	*newcon = strdup(buf);
51f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	if (!(*newcon)) {
52f074036424618c130dacb3464465a8b40bffef5Stephen Smalley		ret = -1;
53f074036424618c130dacb3464465a8b40bffef5Stephen Smalley		goto out2;
54f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	}
55f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	ret = 0;
56f074036424618c130dacb3464465a8b40bffef5Stephen Smalley      out2:
57f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	free(buf);
58f074036424618c130dacb3464465a8b40bffef5Stephen Smalley      out:
59f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	close(fd);
60f074036424618c130dacb3464465a8b40bffef5Stephen Smalley	return ret;
61f074036424618c130dacb3464465a8b40bffef5Stephen Smalley}
62