1/* Copyright (C) 2005 Red Hat, Inc. */
2
3struct semanage_user_extra;
4struct semanage_user_key;
5typedef struct semanage_user_extra record_t;
6typedef struct semanage_user_key record_key_t;
7#define DBASE_RECORD_DEFINED
8
9struct dbase_file;
10typedef struct dbase_file dbase_t;
11#define DBASE_DEFINED
12
13#include <stdlib.h>
14#include <stdio.h>
15#include <strings.h>
16
17#include "user_internal.h"
18#include "database_file.h"
19#include "parse_utils.h"
20#include "debug.h"
21#include "handle.h"
22
23static int user_extra_print(semanage_handle_t * handle,
24			    semanage_user_extra_t * user_extra, FILE * str)
25{
26
27	const char *name = semanage_user_extra_get_name(user_extra);
28	const char *prefix = semanage_user_extra_get_prefix(user_extra);
29
30	if (fprintf(str, "user %s prefix %s;\n", name, prefix) < 0)
31		goto err;
32
33	return STATUS_SUCCESS;
34
35      err:
36	ERR(handle, "could not print user extra data "
37	    "for %s to stream", name);
38	return STATUS_ERR;
39}
40
41static int user_extra_parse(semanage_handle_t * handle,
42			    parse_info_t * info,
43			    semanage_user_extra_t * user_extra)
44{
45
46	char *str = NULL;
47
48	if (parse_skip_space(handle, info) < 0)
49		goto err;
50	if (!info->ptr)
51		goto last;
52
53	/* User string */
54	if (parse_assert_str(handle, info, "user") < 0)
55		goto err;
56	if (parse_assert_space(handle, info) < 0)
57		goto err;
58
59	/* Extract name */
60	if (parse_fetch_string(handle, info, &str, ' ') < 0)
61		goto err;
62	if (semanage_user_extra_set_name(handle, user_extra, str) < 0)
63		goto err;
64	free(str);
65	str = NULL;
66
67	/* Prefix string */
68	if (parse_assert_space(handle, info) < 0)
69		goto err;
70	if (parse_assert_str(handle, info, "prefix") < 0)
71		goto err;
72	if (parse_assert_space(handle, info) < 0)
73		goto err;
74
75	/* Extract prefix */
76	if (parse_fetch_string(handle, info, &str, ';') < 0)
77		goto err;
78	if (semanage_user_extra_set_prefix(handle, user_extra, str) < 0)
79		goto err;
80	free(str);
81	str = NULL;
82
83	/* Semicolon */
84	if (parse_skip_space(handle, info) < 0)
85		goto err;
86	if (parse_assert_ch(handle, info, ';') < 0)
87		goto err;
88
89	return STATUS_SUCCESS;
90
91      last:
92	parse_dispose_line(info);
93	return STATUS_NODATA;
94
95      err:
96	ERR(handle, "could not parse user extra data");
97	free(str);
98	parse_dispose_line(info);
99	return STATUS_ERR;
100}
101
102/* USER EXTRA RECORD: FILE extension: method table */
103record_file_table_t SEMANAGE_USER_EXTRA_FILE_RTABLE = {
104	.parse = user_extra_parse,
105	.print = user_extra_print,
106};
107
108int user_extra_file_dbase_init(semanage_handle_t * handle,
109			       const char *path_ro,
110			       const char *path_rw,
111			       dbase_config_t * dconfig)
112{
113
114	if (dbase_file_init(handle,
115			    path_ro,
116			    path_rw,
117			    &SEMANAGE_USER_EXTRA_RTABLE,
118			    &SEMANAGE_USER_EXTRA_FILE_RTABLE,
119			    &dconfig->dbase) < 0)
120		return STATUS_ERR;
121
122	dconfig->dtable = &SEMANAGE_FILE_DTABLE;
123	return STATUS_SUCCESS;
124}
125
126void user_extra_file_dbase_release(dbase_config_t * dconfig)
127{
128
129	dbase_file_release(dconfig->dbase);
130}
131