00001
00002
00003
00004
00005
00006
00007
00008
#include <linux/config.h>
00009
#include <linux/module.h>
00010
#include <linux/types.h>
00011
#include <linux/kernel.h>
00012
#include <linux/string.h>
00013
00014
#include <linux/sched.h>
00015
#include <linux/smp.h>
00016
#include <linux/smp_lock.h>
00017
00018
#include <linux/fs.h>
00019
#include <asm/uaccess.h>
00020
00021
#include <rsbac/types.h>
00022
#include <rsbac/reg.h>
00023
#include <rsbac/adf.h>
00024
#include <rsbac/aci.h>
00025
#include <rsbac/aci_data_structures.h>
00026
#include <rsbac/getname.h>
00027
#include <rsbac/error.h>
00028
#include <rsbac/proc_fs.h>
00029
00030 static u_long
nr_request_calls = 0;
00031 static u_long
nr_set_attr_calls = 0;
00032 static u_long
nr_need_overwrite_calls = 0;
00033 static boolean no_write =
FALSE;
00034 static u_long
nr_system_calls = 0;
00035 static void *
system_call_arg = 0;
00036
00037
MODULE_AUTHOR(
"Amon Ott");
00038
MODULE_DESCRIPTION(
"RSBAC REG sample decision module 2");
00039
00040
MODULE_PARM(name,
"s");
00041 static char *
name =
NULL;
00042 static char dummy_buf[70]=
"To protect against wrong insmod params";
00043
00044
MODULE_PARM(syscall_name,
"s");
00045 static char *
syscall_name =
NULL;
00046 static char dummy_buf2[70]=
"To protect against wrong insmod params";
00047
00048
MODULE_PARM(handle,
"l");
00049 static long handle = 123457;
00050
00051
MODULE_PARM(syscall_registration_handle,
"l");
00052 static long syscall_registration_handle = 754321;
00053
MODULE_PARM(syscall_dispatcher_handle,
"l");
00054 static long syscall_dispatcher_handle = 2;
00055
00056
00057 #define FILENAME "regsmp2"
00058
00059
00060 #define FILE_VERSION 1
00061
00062
00063
00064
#if defined(CONFIG_RSBAC_PROC)
00065
#define PROC_NAME "reg_sample2"
00066
static struct proc_dir_entry * proc_reg_sample_p;
00067
00068
#if LINUX_VERSION_CODE < KERNEL_VERSION(2,3,0)
00069
static int
00070 adf_sample_proc_info(
char *buffer,
char **start, off_t offset,
int length,
int dummy)
00071 #
else
00072
static int
00073 adf_sample_proc_info(
char *buffer,
char **start, off_t offset,
int length)
00074 #endif
00075 {
00076
int len = 0;
00077 off_t pos = 0;
00078 off_t begin = 0;
00079
00080
union rsbac_target_id_t rsbac_target_id;
00081
union rsbac_attribute_value_t rsbac_attribute_value;
00082
00083
if (!
rsbac_is_initialized())
00084
return (-ENOSYS);
00085
00086 rsbac_target_id.
scd =
ST_rsbac;
00087 rsbac_attribute_value.
dummy = 0;
00088
if (!
rsbac_adf_request(
R_GET_STATUS_DATA,
00089 current->pid,
00090
T_SCD,
00091 rsbac_target_id,
00092
A_none,
00093 rsbac_attribute_value))
00094 {
00095
return -EPERM;
00096 }
00097 len += sprintf(buffer,
"RSBAC REG decision module sample 2\n----------------------------------\n");
00098 pos = begin + len;
00099
if (pos < offset)
00100 {
00101 len = 0;
00102 begin = pos;
00103 }
00104
if (pos > offset+length)
00105
goto out;
00106
00107 len += sprintf(buffer + len,
"%lu calls to request function.\n",
00108
nr_request_calls);
00109 pos = begin + len;
00110
if (pos < offset)
00111 {
00112 len = 0;
00113 begin = pos;
00114 }
00115
if (pos > offset+length)
00116
goto out;
00117
00118 len += sprintf(buffer + len,
"%lu calls to set_attr function.\n",
00119
nr_set_attr_calls);
00120 pos = begin + len;
00121
if (pos < offset)
00122 {
00123 len = 0;
00124 begin = pos;
00125 }
00126
if (pos > offset+length)
00127
goto out;
00128
00129 len += sprintf(buffer + len,
"%lu calls to need_overwrite function.\n",
00130
nr_need_overwrite_calls);
00131 pos = begin + len;
00132
if (pos < offset)
00133 {
00134 len = 0;
00135 begin = pos;
00136 }
00137
if (pos > offset+length)
00138
goto out;
00139
00140 len += sprintf(buffer + len,
"%lu calls to system_call function %lu, last arg was %p.\n",
00141
nr_system_calls,
00142
syscall_dispatcher_handle,
00143
system_call_arg);
00144 pos = begin + len;
00145
if (pos < offset)
00146 {
00147 len = 0;
00148 begin = pos;
00149 }
00150
if (pos > offset+length)
00151
goto out;
00152
00153 out:
00154 *start = buffer + (offset - begin);
00155 len -= (offset - begin);
00156
00157
if (len > length)
00158 len = length;
00159
return len;
00160 }
00161
#endif
00162
00163
00164
00165
00166
00167
00168
00169 static int read_info(
void)
00170 {
00171
struct file file;
00172
char name[
RSBAC_MAXNAMELEN];
00173
int err = 0;
00174
int tmperr;
00175 mm_segment_t oldfs;
00176 u_int version;
00177 u_long tmpval;
00178
00179
00180 strcpy(
name,
FILENAME);
00181
00182
00183
if ((err =
rsbac_read_open(
name,
00184 &file,
00185
rsbac_root_dev) ))
00186
return(err);
00187
00188
00189
00190
00191
00192
00193
00194
00195
00196
00197
00198 oldfs = get_fs();
00199 set_fs(KERNEL_DS);
00200
00201 tmperr = file.f_op->read(&file,
00202 (
char *) &version,
00203
sizeof(version),
00204 &file.f_pos);
00205
00206
if (tmperr <
sizeof(version))
00207 {
00208 printk(KERN_WARNING
00209
"read_info(): read error from file!\n");
00210 err = -
RSBAC_EREADFAILED;
00211
goto end_read;
00212 }
00213
00214
if (version !=
FILE_VERSION)
00215 {
00216 printk(KERN_WARNING
00217
"read_info(): wrong version %u, expected %u - skipping file and setting no_write!\n",
00218 version,
FILE_VERSION);
00219
no_write =
TRUE;
00220 err = -
RSBAC_EREADFAILED;
00221
goto end_read;
00222 }
00223
00224
00225 tmperr = file.f_op->read(&file,
00226 (
char *) &tmpval,
00227
sizeof(tmpval),
00228 &file.f_pos);
00229
if (tmperr <
sizeof(tmpval))
00230 {
00231 printk(KERN_WARNING
"%s\n",
00232
"read_info(): read error from file!");
00233 err = -
RSBAC_EREADFAILED;
00234
goto end_read;
00235 }
00236
nr_request_calls = tmpval;
00237
00238
00239 tmperr = file.f_op->read(&file,
00240 (
char *) &tmpval,
00241
sizeof(tmpval),
00242 &file.f_pos);
00243
if (tmperr <
sizeof(tmpval))
00244 {
00245 printk(KERN_WARNING
"%s\n",
00246
"read_info(): read error from file!");
00247 err = -
RSBAC_EREADFAILED;
00248
goto end_read;
00249 }
00250
nr_set_attr_calls = tmpval;
00251
00252
00253 tmperr = file.f_op->read(&file,
00254 (
char *) &tmpval,
00255
sizeof(tmpval),
00256 &file.f_pos);
00257
if (tmperr <
sizeof(tmpval))
00258 {
00259 printk(KERN_WARNING
"%s\n",
00260
"read_info(): read error from file!");
00261 err = -
RSBAC_EREADFAILED;
00262
goto end_read;
00263 }
00264
nr_need_overwrite_calls = tmpval;
00265
00266 end_read:
00267
00268
00269 set_fs(oldfs);
00270
00271
00272
rsbac_read_close(&file);
00273
00274
00275
return(err);
00276 };
00277
00278 static int write_info(
void)
00279 {
00280
struct file file;
00281
char name[
RSBAC_MAXNAMELEN];
00282
int err = 0;
00283
int tmperr;
00284 mm_segment_t oldfs;
00285 u_int version =
FILE_VERSION;
00286
00287
00288 strcpy(
name,
FILENAME);
00289
00290
00291 down(&
rsbac_write_sem);
00292
00293
00294
if ((err =
rsbac_write_open(
name,
00295 &file,
00296
rsbac_root_dev) ))
00297 {
00298 up(&
rsbac_write_sem);
00299
return(err);
00300 }
00301
00302
00303
00304
00305
00306
00307
00308
00309 oldfs = get_fs();
00310 set_fs(KERNEL_DS);
00311
00312 tmperr = file.f_op->write(&file,
00313 (
char *) &version,
00314
sizeof(version),
00315 &file.f_pos);
00316
if (tmperr <
sizeof(version))
00317 {
00318 printk(KERN_WARNING
00319
"write_info(): write error %i on file!\n",
00320 tmperr);
00321 err = -
RSBAC_EWRITEFAILED;
00322
goto end_write;
00323 }
00324
00325 tmperr = file.f_op->write(&file,
00326 (
char *) &
nr_request_calls,
00327
sizeof(
nr_request_calls),
00328 &file.f_pos);
00329
if (tmperr <
sizeof(
nr_request_calls))
00330 {
00331 printk(KERN_WARNING
00332
"write_info(): write error %i on file!\n",
00333 tmperr);
00334 err = -
RSBAC_EWRITEFAILED;
00335
goto end_write;
00336 }
00337
00338 tmperr = file.f_op->write(&file,
00339 (
char *) &
nr_set_attr_calls,
00340
sizeof(
nr_set_attr_calls),
00341 &file.f_pos);
00342
if (tmperr <
sizeof(
nr_set_attr_calls))
00343 {
00344 printk(KERN_WARNING
00345
"write_info(): write error %i on file!\n",
00346 tmperr);
00347 err = -
RSBAC_EWRITEFAILED;
00348
goto end_write;
00349 }
00350
00351 tmperr = file.f_op->write(&file,
00352 (
char *) &
nr_need_overwrite_calls,
00353
sizeof(
nr_need_overwrite_calls),
00354 &file.f_pos);
00355
if (tmperr <
sizeof(
nr_need_overwrite_calls))
00356 {
00357 printk(KERN_WARNING
00358
"write_info(): write error %i on file!\n",
00359 tmperr);
00360 err = -
RSBAC_EWRITEFAILED;
00361
goto end_write;
00362 }
00363
00364 end_write:
00365
00366
00367 set_fs(oldfs);
00368
00369
00370
rsbac_write_close(&file);
00371 up(&
rsbac_write_sem);
00372
return(err);
00373 };
00374
00375
00376
00377
00378 static int request_func (
enum rsbac_adf_request_t request,
00379
rsbac_pid_t owner_pid,
00380
enum rsbac_target_t target,
00381
union rsbac_target_id_t tid,
00382
enum rsbac_attribute_t attr,
00383
union rsbac_attribute_value_t attr_val,
00384
rsbac_uid_t owner)
00385 {
00386
00387
if(request !=
R_SEARCH)
00388
nr_request_calls++;
00389
return GRANTED;
00390 }
00391
00392 static int set_attr_func (
enum rsbac_adf_request_t request,
00393
rsbac_pid_t owner_pid,
00394
enum rsbac_target_t target,
00395
union rsbac_target_id_t tid,
00396
enum rsbac_target_t new_target,
00397
union rsbac_target_id_t new_tid,
00398
enum rsbac_attribute_t attr,
00399
union rsbac_attribute_value_t attr_val,
00400
rsbac_uid_t owner)
00401 {
00402
00403
if(request !=
R_SEARCH)
00404
nr_set_attr_calls++;
00405
return 0;
00406 }
00407
00408 static boolean need_overwrite_func (
struct dentry * dentry_p)
00409 {
00410
nr_need_overwrite_calls++;
00411
return FALSE;
00412 }
00413
00414 static int write_func(
boolean need_lock)
00415 {
00416
int res=0;
00417
00418
if(need_lock)
00419 lock_kernel();
00420
00421
if(!
write_info())
00422 res = 1;
00423
00424
if(need_lock)
00425 unlock_kernel();
00426
00427
return(res);
00428 }
00429
00430 static int syscall_func (
void * arg)
00431 {
00432
nr_system_calls++;
00433
system_call_arg = arg;
00434
return nr_system_calls;
00435 }
00436
00437
00438
00439 int init_module(
void)
00440 {
00441
struct rsbac_reg_entry_t entry;
00442
struct rsbac_reg_syscall_entry_t syscall_entry;
00443
00444
if(!
handle)
00445
handle = 123457;
00446
if(!
syscall_registration_handle)
00447
syscall_registration_handle = 754321;
00448
if(!
syscall_dispatcher_handle)
00449
syscall_dispatcher_handle = 2;
00450
00451 printk(KERN_INFO
"RSBAC REG decision module sample 2: Initializing.\n");
00452
00453
00454 memset(&entry, 0,
sizeof(entry));
00455 memset(&syscall_entry, 0,
sizeof(syscall_entry));
00456
00457
if((
dummy_buf[0] !=
'T') || (
dummy_buf2[0] !=
'T'))
00458 {
00459 printk(KERN_WARNING
"RSBAC REG decision module sample 2: Not loaded due to invalid param string.\n");
00460
return -ENOEXEC;
00461 }
00462
if(
name)
00463 {
00464 strncpy(entry.name,
name,
RSBAC_REG_NAME_LEN);
00465 entry.name[
RSBAC_REG_NAME_LEN] = 0;
00466 }
00467
else
00468 strcpy(entry.name,
"RSBAC REG sample 2 ADF module");
00469 printk(KERN_INFO
"RSBAC REG decision module sample 2: REG Version: %u, Name: %s, Handle: %li\n",
00470
RSBAC_REG_VERSION, entry.name,
handle);
00471
00472 entry.handle =
handle;
00473 entry.request_func =
request_func;
00474 entry.set_attr_func =
set_attr_func;
00475 entry.need_overwrite_func =
need_overwrite_func;
00476 entry.write_func =
write_func;
00477 entry.switch_on =
TRUE;
00478
00479 printk(KERN_INFO
"RSBAC REG decision module sample 2: Registering to ADF.\n");
00480
if(
rsbac_reg_register(
RSBAC_REG_VERSION, entry) < 0)
00481 {
00482 printk(KERN_WARNING
"RSBAC REG decision module sample 2: Registering failed. Unloading.\n");
00483
return -ENOEXEC;
00484 }
00485
00486
if(
syscall_name)
00487 {
00488 strncpy(syscall_entry.name,
syscall_name,
RSBAC_REG_NAME_LEN);
00489 syscall_entry.name[
RSBAC_REG_NAME_LEN] = 0;
00490 }
00491
else
00492 strcpy(syscall_entry.name,
"RSBAC REG sample 2 syscall");
00493 printk(KERN_INFO
"RSBAC REG decision module sample 2: REG Version: %u, Name: %s, Dispatcher Handle: %li\n",
00494
RSBAC_REG_VERSION, syscall_entry.name,
syscall_dispatcher_handle);
00495
00496 syscall_entry.registration_handle =
syscall_registration_handle;
00497 syscall_entry.dispatcher_handle =
syscall_dispatcher_handle;
00498 syscall_entry.syscall_func =
syscall_func;
00499
00500 printk(KERN_INFO
"RSBAC REG decision module sample 2: Registering syscall.\n");
00501
syscall_registration_handle =
rsbac_reg_register_syscall(
RSBAC_REG_VERSION, syscall_entry);
00502
if(
syscall_registration_handle < 0)
00503 {
00504 printk(KERN_WARNING
"RSBAC REG decision module sample 2: Registering syscall failed. Unloading.\n");
00505
if(
rsbac_reg_unregister(
handle))
00506 {
00507 printk(KERN_ERR
"RSBAC REG decision module sample 2: Unregistering failed - beware of possible system failure!\n");
00508 }
00509
return -ENOEXEC;
00510 }
00511
00512
if(
read_info())
00513 {
00514 printk(KERN_WARNING
00515
"RSBAC REG decision module sample 2: Could not read info from previous session.\n");
00516 }
00517
00518
#if defined(CONFIG_RSBAC_PROC)
00519
proc_reg_sample_p = create_proc_entry(PROC_NAME,
00520 S_IFREG | S_IRUGO,
00521
proc_rsbac_root_p);
00522
if(!proc_reg_sample_p)
00523 {
00524 printk(KERN_WARNING
"%s: Not loaded due to failed proc entry registering.\n",
name);
00525
if(
rsbac_reg_unregister_syscall(
syscall_registration_handle))
00526 {
00527 printk(KERN_ERR
"RSBAC REG decision module sample 2: Unregistering syscall failed - beware of possible system failure!\n");
00528 }
00529
if(
rsbac_reg_unregister(
handle))
00530 {
00531 printk(KERN_ERR
"RSBAC REG decision module sample 2: Unregistering from ADF failed - beware of possible system failure!\n");
00532 }
00533
return -ENOEXEC;
00534 }
00535 proc_reg_sample_p->get_info = adf_sample_proc_info;
00536
#endif
00537
00538 printk(KERN_INFO
"RSBAC REG decision module sample 2: Loaded.\n");
00539
00540
return 0;
00541 }
00542
00543 void cleanup_module(
void)
00544 {
00545 printk(KERN_INFO
"RSBAC REG decision module sample 2: Unregistering.\n");
00546
#if defined(CONFIG_RSBAC_PROC)
00547
remove_proc_entry(PROC_NAME,
proc_rsbac_root_p);
00548
#endif
00549
if(
write_info())
00550 {
00551 printk(KERN_WARNING
00552
"RSBAC REG decision module sample 2: Could not save info for next session.\n");
00553 }
00554
if(
rsbac_reg_unregister_syscall(
syscall_registration_handle))
00555 {
00556 printk(KERN_ERR
"RSBAC REG decision module sample 2: Unregistering syscall failed - beware of possible system failure!\n");
00557 }
00558
if(
rsbac_reg_unregister(
handle))
00559 {
00560 printk(KERN_ERR
"RSBAC REG decision module sample 2: Unregistering module failed - beware of possible system failure!\n");
00561 }
00562 printk(KERN_INFO
"RSBAC REG decision module sample 2: Unloaded.\n");
00563 }