#!/bin/sh -
#
# FLASK
set -e
awk=$1
shift
# output files
av_permissions="av_permissions.h"
av_inherit="av_inherit.h"
common_perm_to_string="common_perm_to_string.h"
av_perm_to_string="av_perm_to_string.h"
cat $* | $awk "
BEGIN {
outfile = \"$av_permissions\"
inheritfile = \"$av_inherit\"
cpermfile = \"$common_perm_to_string\"
avpermfile = \"$av_perm_to_string\"
"'
nextstate = "COMMON_OR_AV";
printf("/* This file is automatically generated. Do not edit. */\n") > outfile;
printf("/* This file is automatically generated. Do not edit. */\n") > inheritfile;
printf("/* This file is automatically generated. Do not edit. */\n") > cpermfile;
printf("/* This file is automatically generated. Do not edit. */\n") > avpermfile;
;
}
/^[ \t]*#/ {
next;
}
$1 == "common" {
if (nextstate != "COMMON_OR_AV")
{
printf("Parse error: Unexpected COMMON definition on line %d\n", NR);
next;
}
if ($2 in common_defined)
{
printf("Duplicate COMMON definition for %s on line %d.\n", $2, NR);
next;
}
common_defined[$2] = 1;
tclass = $2;
common_name = $2;
permission = 1;
printf("TB_(common_%s_perm_to_string)\n", $2) > cpermfile;
nextstate = "COMMON-OPENBRACKET";
next;
}
$1 == "class" {
if (nextstate != "COMMON_OR_AV" &&
nextstate != "CLASS_OR_CLASS-OPENBRACKET")
{
printf("Parse error: Unexpected class definition on line %d\n", NR);
next;
}
tclass = $2;
if (tclass in av_defined)
{
printf("Duplicate access vector definition for %s on line %d\n", tclass, NR);
next;
}
av_defined[tclass] = 1;
inherits = "";
permission = 1;
nextstate = "INHERITS_OR_CLASS-OPENBRACKET";
next;
}
$1 == "inherits" {
if (nextstate != "INHERITS_OR_CLASS-OPENBRACKET")
{
printf("Parse error: Unexpected INHERITS definition on line %d\n", NR);
next;
}
if (!($2 in common_defined))
{
printf("COMMON %s is not defined (line %d).\n", $2, NR);
next;
}
inherits = $2;
permission = common_base[$2];
for (combined in common_perms)
{
split(combined,separate, SUBSEP);
if (separate[1] == inherits)
{
inherited_perms[common_perms[combined]] = separate[2];
}
}
j = 1;
for (i in inherited_perms) {
ind[j] = i + 0;
j++;
}
n = asort(ind);
for (i = 1; i <= n; i++) {
perm = inherited_perms[ind[i]];
printf("#define %s__%s", toupper(tclass), toupper(perm)) > outfile;
spaces = 40 - (length(perm) + length(tclass));
if (spaces < 1)
spaces = 1;
for (j = 0; j < spaces; j++)
printf(" ") > outfile;
printf("0x%08xUL\n", ind[i]) > outfile;
}
for (i in ind) delete ind[i];
for (i in inherited_perms) delete inherited_perms[i];
printf(" S_(SECCLASS_%s, %s, 0x%08xUL)\n", toupper(tclass), inherits, permission) > inheritfile;
nextstate = "CLASS_OR_CLASS-OPENBRACKET";
next;
}
$1 == "{" {
if (nextstate != "INHERITS_OR_CLASS-OPENBRACKET" &&
nextstate != "CLASS_OR_CLASS-OPENBRACKET" &&
nextstate != "COMMON-OPENBRACKET")
{
printf("Parse error: Unexpected { on line %d\n", NR);
next;
}
if (nextstate == "INHERITS_OR_CLASS-OPENBRACKET")
nextstate = "CLASS-CLOSEBRACKET";
if (nextstate == "CLASS_OR_CLASS-OPENBRACKET")
nextstate = "CLASS-CLOSEBRACKET";
if (nextstate == "COMMON-OPENBRACKET")
nextstate = "COMMON-CLOSEBRACKET";
}
/[a-z][a-z_]*/ {
if (nextstate != "COMMON-CLOSEBRACKET" &&
nextstate != "CLASS-CLOSEBRACKET")
{
printf("Parse error: Unexpected symbol %s on line %d\n", $1, NR);
next;
}
if (nextstate == "COMMON-CLOSEBRACKET")
{
if ((common_name,$1) in common_perms)
{
printf("Duplicate permission %s for common %s on line %d.\n", $1, common_name, NR);
next;
}
common_perms[common_name,$1] = permission;
printf("#define COMMON_%s__%s", toupper(common_name), toupper($1)) > outfile;
printf(" S_(\"%s\")\n", $1) > cpermfile;
}
else
{
if ((tclass,$1) in av_perms)
{
printf("Duplicate permission %s for %s on line %d.\n", $1, tclass, NR);
next;
}
av_perms[tclass,$1] = permission;
if (inherits != "")
{
if ((inherits,$1) in common_perms)
{
printf("Permission %s in %s on line %d conflicts with common permission.\n", $1, tclass, inherits, NR);
next;
}
}
printf("#define %s__%s", toupper(tclass), toupper($1)) > outfile;
printf(" S_(SECCLASS_%s, %s__%s, \"%s\")\n", toupper(tclass), toupper(tclass), toupper($1), $1) > avpermfile;
}
spaces = 40 - (length($1) + length(tclass));
if (spaces < 1)
spaces = 1;
for (i = 0; i < spaces; i++)
printf(" ") > outfile;
printf("0x%08xUL\n", permission) > outfile;
permission = permission * 2;
}
$1 == "}" {
if (nextstate != "CLASS-CLOSEBRACKET" &&
nextstate != "COMMON-CLOSEBRACKET")
{
printf("Parse error: Unexpected } on line %d\n", NR);
next;
}
if (nextstate == "COMMON-CLOSEBRACKET")
{
common_base[common_name] = permission;
printf("TE_(common_%s_perm_to_string)\n\n", common_name) > cpermfile;
}
nextstate = "COMMON_OR_AV";
}
END {
if (nextstate != "COMMON_OR_AV" && nextstate != "CLASS_OR_CLASS-OPENBRACKET")
printf("Parse error: Unexpected end of file\n");
}'
# FLASK