PostgreSQL Source Code  git master
selinux.c File Reference
#include "postgres.h"
#include "lib/stringinfo.h"
#include "sepgsql.h"
Include dependency graph for selinux.c:

Go to the source code of this file.

Functions

bool sepgsql_is_enabled (void)
 
int sepgsql_get_mode (void)
 
int sepgsql_set_mode (int new_mode)
 
bool sepgsql_getenforce (void)
 
void sepgsql_audit_log (bool denied, const char *scontext, const char *tcontext, uint16 tclass, uint32 audited, const char *audit_name)
 
void sepgsql_compute_avd (const char *scontext, const char *tcontext, uint16 tclass, struct av_decision *avd)
 
char * sepgsql_compute_create (const char *scontext, const char *tcontext, uint16 tclass, const char *objname)
 
bool sepgsql_check_perms (const char *scontext, const char *tcontext, uint16 tclass, uint32 required, const char *audit_name, bool abort_on_violation)
 

Variables

struct {
   const char *   class_name
 
   uint16   class_code
 
   struct {
      const char *   av_name
 
      uint32   av_code
 
   }   av [32]
 
selinux_catalog []
 
static int sepgsql_mode = SEPGSQL_MODE_INTERNAL
 

Function Documentation

◆ sepgsql_audit_log()

void sepgsql_audit_log ( bool  denied,
const char *  scontext,
const char *  tcontext,
uint16  tclass,
uint32  audited,
const char *  audit_name 
)

Definition at line 678 of file selinux.c.

References appendStringInfo(), appendStringInfoString(), Assert, av_name, buf, class_name, StringInfoData::data, ereport, errmsg(), i, initStringInfo(), LOG, selinux_catalog, and SEPG_CLASS_MAX.

Referenced by sepgsql_avc_check_perms_label(), and sepgsql_check_perms().

684 {
686  const char *class_name;
687  const char *av_name;
688  int i;
689 
690  /* lookup name of the object class */
691  Assert(tclass < SEPG_CLASS_MAX);
692  class_name = selinux_catalog[tclass].class_name;
693 
694  /* lookup name of the permissions */
695  initStringInfo(&buf);
696  appendStringInfo(&buf, "%s {",
697  (denied ? "denied" : "allowed"));
698  for (i = 0; selinux_catalog[tclass].av[i].av_name; i++)
699  {
700  if (audited & (1UL << i))
701  {
702  av_name = selinux_catalog[tclass].av[i].av_name;
703  appendStringInfo(&buf, " %s", av_name);
704  }
705  }
706  appendStringInfoString(&buf, " }");
707 
708  /*
709  * Call external audit module, if loaded
710  */
711  appendStringInfo(&buf, " scontext=%s tcontext=%s tclass=%s",
712  scontext, tcontext, class_name);
713  if (audit_name)
714  appendStringInfo(&buf, " name=\"%s\"", audit_name);
715 
716  ereport(LOG, (errmsg("SELinux: %s", buf.data)));
717 }
static struct @17 selinux_catalog[]
#define SEPG_CLASS_MAX
Definition: sepgsql.h:54
const char * av_name
Definition: selinux.c:36
#define LOG
Definition: elog.h:26
void appendStringInfo(StringInfo str, const char *fmt,...)
Definition: stringinfo.c:91
void appendStringInfoString(StringInfo str, const char *s)
Definition: stringinfo.c:176
static char * buf
Definition: pg_test_fsync.c:68
void initStringInfo(StringInfo str)
Definition: stringinfo.c:59
#define ereport(elevel,...)
Definition: elog.h:144
#define Assert(condition)
Definition: c.h:746
const char * class_name
Definition: selinux.c:32
int errmsg(const char *fmt,...)
Definition: elog.c:821
int i

◆ sepgsql_check_perms()

bool sepgsql_check_perms ( const char *  scontext,
const char *  tcontext,
uint16  tclass,
uint32  required,
const char *  audit_name,
bool  abort_on_violation 
)

Definition at line 899 of file selinux.c.

References ereport, errcode(), ERRCODE_INSUFFICIENT_PRIVILEGE, errmsg(), ERROR, generate_unaccent_rules::required, sepgsql_audit_log(), sepgsql_compute_avd(), sepgsql_get_debug_audit(), sepgsql_getenforce(), sepgsql_mode, and SEPGSQL_MODE_INTERNAL.

905 {
906  struct av_decision avd;
907  uint32 denied;
908  uint32 audited;
909  bool result = true;
910 
911  sepgsql_compute_avd(scontext, tcontext, tclass, &avd);
912 
913  denied = required & ~avd.allowed;
914 
916  audited = (denied ? denied : required);
917  else
918  audited = (denied ? (denied & avd.auditdeny)
919  : (required & avd.auditallow));
920 
921  if (denied &&
922  sepgsql_getenforce() > 0 &&
923  (avd.flags & SELINUX_AVD_FLAGS_PERMISSIVE) == 0)
924  result = false;
925 
926  /*
927  * It records a security audit for the request, if needed. But, when
928  * SE-PgSQL performs 'internal' mode, it needs to keep silent.
929  */
930  if (audited && sepgsql_mode != SEPGSQL_MODE_INTERNAL)
931  {
932  sepgsql_audit_log(denied,
933  scontext,
934  tcontext,
935  tclass,
936  audited,
937  audit_name);
938  }
939 
940  if (!result && abort_on_violation)
941  ereport(ERROR,
943  errmsg("SELinux: security policy violation")));
944  return result;
945 }
#define SEPGSQL_MODE_INTERNAL
Definition: sepgsql.h:30
static int sepgsql_mode
Definition: selinux.c:610
void sepgsql_compute_avd(const char *scontext, const char *tcontext, uint16 tclass, struct av_decision *avd)
Definition: selinux.c:733
int errcode(int sqlerrcode)
Definition: elog.c:610
bool sepgsql_getenforce(void)
Definition: selinux.c:651
#define ERRCODE_INSUFFICIENT_PRIVILEGE
#define ERROR
Definition: elog.h:43
void sepgsql_audit_log(bool denied, const char *scontext, const char *tcontext, uint16 tclass, uint32 audited, const char *audit_name)
Definition: selinux.c:678
bool sepgsql_get_debug_audit(void)
Definition: hooks.c:75
unsigned int uint32
Definition: c.h:375
#define ereport(elevel,...)
Definition: elog.h:144
int errmsg(const char *fmt,...)
Definition: elog.c:821

◆ sepgsql_compute_avd()

void sepgsql_compute_avd ( const char *  scontext,
const char *  tcontext,
uint16  tclass,
struct av_decision *  avd 
)

Definition at line 733 of file selinux.c.

References Assert, av_code, av_name, class_code, ereport, errcode(), errmsg(), ERROR, i, selinux_catalog, and SEPG_CLASS_MAX.

Referenced by sepgsql_avc_compute(), and sepgsql_check_perms().

737 {
738  const char *tclass_name;
739  security_class_t tclass_ex;
740  struct av_decision avd_ex;
741  int i,
742  deny_unknown = security_deny_unknown();
743 
744  /* Get external code of the object class */
745  Assert(tclass < SEPG_CLASS_MAX);
746  Assert(tclass == selinux_catalog[tclass].class_code);
747 
748  tclass_name = selinux_catalog[tclass].class_name;
749  tclass_ex = string_to_security_class(tclass_name);
750 
751  if (tclass_ex == 0)
752  {
753  /*
754  * If the current security policy does not support permissions
755  * corresponding to database objects, we fill up them with dummy data.
756  * If security_deny_unknown() returns positive value, undefined
757  * permissions should be denied. Otherwise, allowed
758  */
759  avd->allowed = (security_deny_unknown() > 0 ? 0 : ~0);
760  avd->auditallow = 0U;
761  avd->auditdeny = ~0U;
762  avd->flags = 0;
763 
764  return;
765  }
766 
767  /*
768  * Ask SELinux what is allowed set of permissions on a pair of the
769  * security contexts and the given object class.
770  */
771  if (security_compute_av_flags_raw(scontext,
772  tcontext,
773  tclass_ex, 0, &avd_ex) < 0)
774  ereport(ERROR,
775  (errcode(ERRCODE_INTERNAL_ERROR),
776  errmsg("SELinux could not compute av_decision: "
777  "scontext=%s tcontext=%s tclass=%s: %m",
778  scontext, tcontext, tclass_name)));
779 
780  /*
781  * SELinux returns its access control decision as a set of permissions
782  * represented in external code which depends on run-time environment. So,
783  * we need to translate it to the internal representation before returning
784  * results for the caller.
785  */
786  memset(avd, 0, sizeof(struct av_decision));
787 
788  for (i = 0; selinux_catalog[tclass].av[i].av_name; i++)
789  {
790  access_vector_t av_code_ex;
791  const char *av_name = selinux_catalog[tclass].av[i].av_name;
792  uint32 av_code = selinux_catalog[tclass].av[i].av_code;
793 
794  av_code_ex = string_to_av_perm(tclass_ex, av_name);
795  if (av_code_ex == 0)
796  {
797  /* fill up undefined permissions */
798  if (!deny_unknown)
799  avd->allowed |= av_code;
800  avd->auditdeny |= av_code;
801 
802  continue;
803  }
804 
805  if (avd_ex.allowed & av_code_ex)
806  avd->allowed |= av_code;
807  if (avd_ex.auditallow & av_code_ex)
808  avd->auditallow |= av_code;
809  if (avd_ex.auditdeny & av_code_ex)
810  avd->auditdeny |= av_code;
811  }
812 }
static struct @17 selinux_catalog[]
#define SEPG_CLASS_MAX
Definition: sepgsql.h:54
const char * av_name
Definition: selinux.c:36
int errcode(int sqlerrcode)
Definition: elog.c:610
#define ERROR
Definition: elog.h:43
uint32 av_code
Definition: selinux.c:37
unsigned int uint32
Definition: c.h:375
#define ereport(elevel,...)
Definition: elog.h:144
uint16 class_code
Definition: selinux.c:33
#define Assert(condition)
Definition: c.h:746
int errmsg(const char *fmt,...)
Definition: elog.c:821
int i

◆ sepgsql_compute_create()

char* sepgsql_compute_create ( const char *  scontext,
const char *  tcontext,
uint16  tclass,
const char *  objname 
)

Definition at line 836 of file selinux.c.

References Assert, ereport, errcode(), errmsg(), ERROR, PG_END_TRY, PG_FINALLY, PG_TRY, pstrdup(), selinux_catalog, and SEPG_CLASS_MAX.

Referenced by sepgsql_attribute_post_create(), sepgsql_avc_compute(), sepgsql_database_post_create(), sepgsql_proc_post_create(), sepgsql_relation_post_create(), and sepgsql_schema_post_create().

840 {
841  char *ncontext;
842  security_class_t tclass_ex;
843  const char *tclass_name;
844  char *result;
845 
846  /* Get external code of the object class */
847  Assert(tclass < SEPG_CLASS_MAX);
848 
849  tclass_name = selinux_catalog[tclass].class_name;
850  tclass_ex = string_to_security_class(tclass_name);
851 
852  /*
853  * Ask SELinux what is the default context for the given object class on a
854  * pair of security contexts
855  */
856  if (security_compute_create_name_raw(scontext,
857  tcontext,
858  tclass_ex,
859  objname,
860  &ncontext) < 0)
861  ereport(ERROR,
862  (errcode(ERRCODE_INTERNAL_ERROR),
863  errmsg("SELinux could not compute a new context: "
864  "scontext=%s tcontext=%s tclass=%s: %m",
865  scontext, tcontext, tclass_name)));
866 
867  /*
868  * libselinux returns malloc()'ed string, so we need to copy it on the
869  * palloc()'ed region.
870  */
871  PG_TRY();
872  {
873  result = pstrdup(ncontext);
874  }
875  PG_FINALLY();
876  {
877  freecon(ncontext);
878  }
879  PG_END_TRY();
880 
881  return result;
882 }
static struct @17 selinux_catalog[]
#define SEPG_CLASS_MAX
Definition: sepgsql.h:54
char * pstrdup(const char *in)
Definition: mcxt.c:1187
int errcode(int sqlerrcode)
Definition: elog.c:610
#define ERROR
Definition: elog.h:43
#define PG_FINALLY()
Definition: elog.h:312
#define ereport(elevel,...)
Definition: elog.h:144
#define Assert(condition)
Definition: c.h:746
int errmsg(const char *fmt,...)
Definition: elog.c:821
#define PG_TRY()
Definition: elog.h:295
#define PG_END_TRY()
Definition: elog.h:320

◆ sepgsql_get_mode()

int sepgsql_get_mode ( void  )

Definition at line 625 of file selinux.c.

References sepgsql_mode.

Referenced by sepgsql_avc_check_perms_label().

626 {
627  return sepgsql_mode;
628 }
static int sepgsql_mode
Definition: selinux.c:610

◆ sepgsql_getenforce()

bool sepgsql_getenforce ( void  )

Definition at line 651 of file selinux.c.

References sepgsql_mode, and SEPGSQL_MODE_DEFAULT.

Referenced by check_relation_privileges(), sepgsql_avc_check_perms_label(), sepgsql_check_perms(), and sepgsql_utility_command().

652 {
654  selinux_status_getenforce() > 0)
655  return true;
656 
657  return false;
658 }
static int sepgsql_mode
Definition: selinux.c:610
#define SEPGSQL_MODE_DEFAULT
Definition: sepgsql.h:28

◆ sepgsql_is_enabled()

bool sepgsql_is_enabled ( void  )

Definition at line 616 of file selinux.c.

References sepgsql_mode, and SEPGSQL_MODE_DISABLED.

Referenced by sepgsql_getcon(), sepgsql_mcstrans_in(), sepgsql_mcstrans_out(), and sepgsql_restorecon().

617 {
618  return (sepgsql_mode != SEPGSQL_MODE_DISABLED ? true : false);
619 }
static int sepgsql_mode
Definition: selinux.c:610
#define SEPGSQL_MODE_DISABLED
Definition: sepgsql.h:31

◆ sepgsql_set_mode()

int sepgsql_set_mode ( int  new_mode)

Definition at line 634 of file selinux.c.

References sepgsql_mode.

Referenced by _PG_init(), and sepgsql_client_auth().

635 {
636  int old_mode = sepgsql_mode;
637 
638  sepgsql_mode = new_mode;
639 
640  return old_mode;
641 }
static int sepgsql_mode
Definition: selinux.c:610

Variable Documentation

◆ av

◆ av_code

uint32 av_code

Definition at line 37 of file selinux.c.

Referenced by sepgsql_compute_avd().

◆ av_name

const char* av_name

Definition at line 36 of file selinux.c.

Referenced by sepgsql_audit_log(), and sepgsql_compute_avd().

◆ class_code

uint16 class_code

Definition at line 33 of file selinux.c.

Referenced by sepgsql_compute_avd().

◆ class_name

const char* class_name

Definition at line 32 of file selinux.c.

Referenced by sepgsql_audit_log(), and to_regclass().

◆ selinux_catalog

struct { ... } selinux_catalog[]

◆ sepgsql_mode