blob: daf8314748bbd69a57871029c7fd78451c54e5a9 [file] [log] [blame]
Joshua Brindle13cd4c82008-08-19 15:30:36 -04001/* Author: James Athey
2 */
3
4%module selinux
5%{
6 #include "selinux/selinux.h"
7%}
8
Joshua Brindle09836bf2009-01-12 10:34:01 -05009%pythoncode %{
10
11import shutil, os, stat
12
13def restorecon(path, recursive=False):
14 """ Restore SELinux context on a given path """
Eric Parisc7ed95f2011-06-29 00:32:30 -040015
16 try:
17 mode = os.lstat(path)[stat.ST_MODE]
18 status, context = matchpathcon(path, mode)
19 except OSError:
20 path = os.path.realpath(os.path.expanduser(path))
21 mode = os.lstat(path)[stat.ST_MODE]
22 status, context = matchpathcon(path, mode)
23
Joshua Brindle09836bf2009-01-12 10:34:01 -050024 if status == 0:
25 lsetfilecon(path, context)
26 if recursive:
27 os.path.walk(path, lambda arg, dirname, fnames:
28 map(restorecon, [os.path.join(dirname, fname)
29 for fname in fnames]), None)
30
Steve Lawrence53772102010-06-10 13:56:57 -040031def chcon(path, context, recursive=False):
32 """ Set the SELinux context on a given path """
33 lsetfilecon(path, context)
34 if recursive:
35 for root, dirs, files in os.walk(path):
36 for name in files + dirs:
37 lsetfilecon(os.path.join(root,name), context)
38
Daniel J Walsh66d07602009-09-16 16:58:12 -040039def copytree(src, dest):
40 """ An SELinux-friendly shutil.copytree method """
41 shutil.copytree(src, dest)
42 restorecon(dest, recursive=True)
43
44def install(src, dest):
45 """ An SELinux-friendly shutil.move method """
46 shutil.move(src, dest)
47 restorecon(dest, recursive=True)
Joshua Brindle09836bf2009-01-12 10:34:01 -050048%}
49
Joshua Brindle13cd4c82008-08-19 15:30:36 -040050/* security_get_boolean_names() typemap */
51%typemap(argout) (char ***names, int *len) {
52 PyObject* list = PyList_New(*$2);
53 int i;
54 for (i = 0; i < *$2; i++) {
Eric Paris63df0f72011-06-28 22:39:40 -040055 PyList_SetItem(list, i, PyBytes_FromString((*$1)[i]));
Joshua Brindle13cd4c82008-08-19 15:30:36 -040056 }
57 $result = SWIG_Python_AppendOutput($result, list);
58}
59
60/* return a sid along with the result */
61%typemap(argout) (security_id_t * sid) {
62 if (*$1) {
63 %append_output(SWIG_NewPointerObj(*$1, $descriptor(security_id_t), 0));
64 } else {
65 Py_INCREF(Py_None);
66 %append_output(Py_None);
67 }
68}
69
70%typemap(in,numinputs=0) security_id_t *(security_id_t temp) {
71 $1 = &temp;
72}
73
74/* Makes security_compute_user() return a Python list of contexts */
75%typemap(argout) (security_context_t **con) {
76 PyObject* plist;
77 int i, len = 0;
78
79 if (*$1) {
80 while((*$1)[len])
81 len++;
82 plist = PyList_New(len);
83 for (i = 0; i < len; i++) {
Eric Paris63df0f72011-06-28 22:39:40 -040084 PyList_SetItem(plist, i,
85 PyBytes_FromString((*$1)[i])
86 );
Joshua Brindle13cd4c82008-08-19 15:30:36 -040087 }
88 } else {
89 plist = PyList_New(0);
90 }
91
92 $result = SWIG_Python_AppendOutput($result, plist);
93}
94
95/* Makes functions in get_context_list.h return a Python list of contexts */
96%typemap(argout) (security_context_t **list) {
97 PyObject* plist;
98 int i;
99
100 if (*$1) {
101 plist = PyList_New(result);
102 for (i = 0; i < result; i++) {
Eric Paris63df0f72011-06-28 22:39:40 -0400103 PyList_SetItem(plist, i,
104 PyBytes_FromString((*$1)[i])
105 );
Joshua Brindle13cd4c82008-08-19 15:30:36 -0400106 }
107 } else {
108 plist = PyList_New(0);
109 }
110 /* Only return the Python list, don't need to return the length anymore */
111 $result = plist;
112}
113
114%typemap(in,noblock=1,numinputs=0) security_context_t * (security_context_t temp = 0) {
115 $1 = &temp;
116}
117%typemap(freearg,match="in") security_context_t * "";
118%typemap(argout,noblock=1) security_context_t * {
119 if (*$1) {
120 %append_output(SWIG_FromCharPtr(*$1));
121 freecon(*$1);
122 }
123 else {
124 Py_INCREF(Py_None);
125 %append_output(Py_None);
126 }
127}
128
129%typemap(in,noblock=1,numinputs=0) char ** (char * temp = 0) {
130 $1 = &temp;
131}
132%typemap(freearg,match="in") char ** "";
133%typemap(argout,noblock=1) char ** {
134 if (*$1) {
135 %append_output(SWIG_FromCharPtr(*$1));
136 free(*$1);
137 }
138 else {
139 Py_INCREF(Py_None);
140 %append_output(Py_None);
141 }
142}
143
144%typemap(in) char * const [] {
145 int i, size;
146 PyObject * s;
147
148 if (!PySequence_Check($input)) {
149 PyErr_SetString(PyExc_ValueError, "Expected a sequence");
150 return NULL;
151 }
152
153 size = PySequence_Size($input);
154
155 $1 = (char**) malloc(size + 1);
156
157 for(i = 0; i < size; i++) {
Eric Paris63df0f72011-06-28 22:39:40 -0400158 if (!PyBytes_Check(PySequence_GetItem($input, i))) {
159 PyErr_SetString(PyExc_ValueError, "Sequence must contain only bytes");
160
Joshua Brindle13cd4c82008-08-19 15:30:36 -0400161 return NULL;
162 }
Eric Paris63df0f72011-06-28 22:39:40 -0400163
Joshua Brindle13cd4c82008-08-19 15:30:36 -0400164 }
165
166 for(i = 0; i < size; i++) {
167 s = PySequence_GetItem($input, i);
Eric Paris63df0f72011-06-28 22:39:40 -0400168
169 $1[i] = (char*) malloc(PyBytes_Size(s) + 1);
170 strcpy($1[i], PyBytes_AsString(s));
171
Joshua Brindle13cd4c82008-08-19 15:30:36 -0400172 }
173 $1[size] = NULL;
174}
175
176%typemap(freearg,match="in") char * const [] {
177 int i = 0;
178 while($1[i]) {
179 free($1[i]);
180 i++;
181 }
182 free($1);
183}
184
Daniel J Walsh66d07602009-09-16 16:58:12 -0400185%include "selinuxswig_python_exception.i"
Joshua Brindle13cd4c82008-08-19 15:30:36 -0400186%include "selinuxswig.i"