Exemplo n.º 1
0
static int notify_check_and_schedule(knot_nameserver_t *nameserver,
                                     const knot_zone_t *zone,
                                     sockaddr_t *from)
{
	if (zone == NULL || from == NULL || knot_zone_data(zone) == NULL) {
		return KNOT_EINVAL;
	}

	/* Check ACL for notify-in. */
	zonedata_t *zd = (zonedata_t *)knot_zone_data(zone);
	if (from) {
		if (acl_match(zd->notify_in, from, 0) == ACL_DENY) {
			/* rfc1996: Ignore request and report incident. */
			return KNOT_EDENIED;
		}
	}

	/* Cancel REFRESH/RETRY timer. */
	evsched_t *sched = ((server_t *)knot_ns_get_data(nameserver))->sched;
	event_t *refresh_ev = zd->xfr_in.timer;
	if (refresh_ev) {
		dbg_notify("notify: expiring REFRESH timer\n");
		evsched_cancel(sched, refresh_ev);

		/* Set REFRESH timer for now. */
		evsched_schedule(sched, refresh_ev, 0);
	}

	return KNOT_EOK;
}
Exemplo n.º 2
0
static void
compare_acls(acl_t acl, struct myacl_t *myacls)
{
	int *marker;
	int entry_id = ACL_FIRST_ENTRY;
	int matched;
	int i, n;
	acl_entry_t acl_entry;

	/* Count ACL entries in myacls array and allocate an indirect array. */
	for (n = 0; myacls[n].name != NULL; ++n)
		continue;
	if (n) {
		marker = malloc(sizeof(marker[0]) * n);
		if (marker == NULL)
			return;
		for (i = 0; i < n; i++)
			marker[i] = i;
	} else
		marker = NULL;

	/*
	 * Iterate over acls in system acl object, try to match each
	 * one with an item in the myacls array.
	 */
	while (1 == acl_get_entry(acl, entry_id, &acl_entry)) {
		/* After the first time... */
		entry_id = ACL_NEXT_ENTRY;

		/* Search for a matching entry (tag and qualifier) */
		for (i = 0, matched = 0; i < n && !matched; i++) {
			if (acl_match(acl_entry, &myacls[marker[i]])) {
				/* We found a match; remove it. */
				marker[i] = marker[n - 1];
				n--;
				matched = 1;
			}
		}

		/* TODO: Print out more details in this case. */
		failure("ACL entry on file that shouldn't be there");
		assert(matched == 1);
	}

	/* Dump entries in the myacls array that weren't in the system acl. */
	for (i = 0; i < n; ++i) {
		failure(" ACL entry missing from file: "
		    "type=%d,permset=%d,tag=%d,qual=%d,name=``%s''\n",
		    myacls[marker[i]].type, myacls[marker[i]].permset,
		    myacls[marker[i]].tag, myacls[marker[i]].qual,
		    myacls[marker[i]].name);
		assert(0); /* Record this as a failure. */
	}
	free(marker);
}
Exemplo n.º 3
0
static void
compare_acls(acl_t acl, struct myacl_t *myacls, const char *filename, int start, int end)
{
	int *marker;
	int entry_id = ACL_FIRST_ENTRY;
	int matched;
	int i, n;
	acl_entry_t acl_entry;

	n = end - start;
	marker = malloc(sizeof(marker[0]) * (n + 1));
	for (i = 0; i < n; i++)
		marker[i] = i + start;
	/* Always include the first ACE. */
	if (start > 0) {
	  marker[n] = 0;
	  ++n;
	}

	/*
	 * Iterate over acls in system acl object, try to match each
	 * one with an item in the myacls array.
	 */
	while (1 == acl_get_entry(acl, entry_id, &acl_entry)) {
		/* After the first time... */
		entry_id = ACL_NEXT_ENTRY;

		/* Search for a matching entry (tag and qualifier) */
		for (i = 0, matched = 0; i < n && !matched; i++) {
			if (acl_match(acl_entry, &myacls[marker[i]])) {
				/* We found a match; remove it. */
				marker[i] = marker[n - 1];
				n--;
				matched = 1;
			}
		}

		failure("ACL entry on file %s that shouldn't be there", filename);
		assert(matched == 1);
	}

	/* Dump entries in the myacls array that weren't in the system acl. */
	for (i = 0; i < n; ++i) {
		failure(" ACL entry %d missing from %s: "
		    "type=%#010x,permset=%#010x,tag=%d,qual=%d,name=``%s''\n",
		    marker[i], filename,
		    myacls[marker[i]].type, myacls[marker[i]].permset,
		    myacls[marker[i]].tag, myacls[marker[i]].qual,
		    myacls[marker[i]].name);
		assert(0); /* Record this as a failure. */
	}
	free(marker);
}
Exemplo n.º 4
0
int main (int argc, char *argv[])
{
	acl *a;
	unsigned long addr;
	acl_contact *c = NULL;
	
	if (argc < 2) return usage(argv[0]);
	addr = atoip (argv[1]);
	if (! addr) return 0;
	
	acl_init ();
	load_config ("/etc/n2/n2rxd.conf");
	a = acl_match (addr);
	if (! a) return 0;
	
	c = acl_get_contacts (a);
	while (c)
	{
		printf ("%s\n", c->contacturl);
		c = c->next;
	}
	return 0;
}
Exemplo n.º 5
0
static void
compare_acls(struct archive_entry *ae, struct acl_t *acls, int n, int mode)
{
	int *marker = malloc(sizeof(marker[0]) * n);
	int i;
	int r;
	int type, permset, tag, qual;
	int matched;
	const char *name;

	for (i = 0; i < n; i++)
		marker[i] = i;

	while (0 == (r = archive_entry_acl_next(ae,
			 ARCHIVE_ENTRY_ACL_TYPE_ACCESS,
			 &type, &permset, &tag, &qual, &name))) {
		for (i = 0, matched = 0; i < n && !matched; i++) {
			if (acl_match(&acls[marker[i]], type, permset,
				tag, qual, name)) {
				/* We found a match; remove it. */
				marker[i] = marker[n - 1];
				n--;
				matched = 1;
			}
		}
		if (tag == ARCHIVE_ENTRY_ACL_USER_OBJ) {
			if (!matched) printf("No match for user_obj perm\n");
			failure("USER_OBJ permset (%02o) != user mode (%02o)",
			    permset, 07 & (mode >> 6));
			assert((permset << 6) == (mode & 0700));
		} else if (tag == ARCHIVE_ENTRY_ACL_GROUP_OBJ) {
			if (!matched) printf("No match for group_obj perm\n");
			failure("GROUP_OBJ permset %02o != group mode %02o",
			    permset, 07 & (mode >> 3));
			assert((permset << 3) == (mode & 0070));
		} else if (tag == ARCHIVE_ENTRY_ACL_OTHER) {
Exemplo n.º 6
0
compare_acls(acl_t acl, struct archive_test_acl_t *myacls, int n)
#endif
{
	int *marker;
	int matched;
	int i;
#if HAVE_SUN_ACL
	int e;
	aclent_t *acl_entry;
#else
	int entry_id = ACL_FIRST_ENTRY;
	acl_entry_t acl_entry;
#endif

	/* Count ACL entries in myacls array and allocate an indirect array. */
	marker = malloc(sizeof(marker[0]) * n);
	if (marker == NULL)
		return;
	for (i = 0; i < n; i++)
		marker[i] = i;

	/*
	 * Iterate over acls in system acl object, try to match each
	 * one with an item in the myacls array.
	 */
#if HAVE_SUN_ACL
	for(e = 0; e < acl->acl_cnt; e++) {
		acl_entry = &((aclent_t *)acl->acl_aclp)[e];
#else
	while (1 == acl_get_entry(acl, entry_id, &acl_entry)) {
		/* After the first time... */
		entry_id = ACL_NEXT_ENTRY;
#endif

		/* Search for a matching entry (tag and qualifier) */
		for (i = 0, matched = 0; i < n && !matched; i++) {
			if (acl_match(acl_entry, &myacls[marker[i]])) {
				/* We found a match; remove it. */
				marker[i] = marker[n - 1];
				n--;
				matched = 1;
			}
		}

		/* TODO: Print out more details in this case. */
		failure("ACL entry on file that shouldn't be there");
		assert(matched == 1);
	}

	/* Dump entries in the myacls array that weren't in the system acl. */
	for (i = 0; i < n; ++i) {
		failure(" ACL entry missing from file: "
		    "type=%#010x,permset=%#010x,tag=%d,qual=%d,name=``%s''\n",
		    myacls[marker[i]].type, myacls[marker[i]].permset,
		    myacls[marker[i]].tag, myacls[marker[i]].qual,
		    myacls[marker[i]].name);
		assert(0); /* Record this as a failure. */
	}
	free(marker);
}

#endif


/*
 * Verify ACL restore-to-disk.  This test is Platform-specific.
 */

DEFINE_TEST(test_acl_platform_posix1e_restore)
{
#if !HAVE_SUN_ACL && !HAVE_POSIX_ACL
	skipping("POSIX.1e ACLs are not supported on this platform");
#else	/* HAVE_SUN_ACL || HAVE_POSIX_ACL */
	struct stat st;
	struct archive *a;
	struct archive_entry *ae;
	int n, fd;
	char *func;
#if HAVE_SUN_ACL
	acl_t *acl, *acl2;
#else
	acl_t acl;
#endif

	/*
	 * First, do a quick manual set/read of ACL data to
	 * verify that the local filesystem does support ACLs.
	 * If it doesn't, we'll simply skip the remaining tests.
	 */
#if HAVE_SUN_ACL
	n = acl_fromtext("user::rwx,user:1:rw-,group::rwx,group:15:r-x,other:rwx,mask:rwx", &acl);
	failure("acl_fromtext(): errno = %d (%s)", errno, strerror(errno));
	assertEqualInt(0, n);
#else
	acl = acl_from_text("u::rwx,u:1:rw,g::rwx,g:15:rx,o::rwx,m::rwx");
	failure("acl_from_text(): errno = %d (%s)", errno, strerror(errno));
	assert((void *)acl != NULL);
#endif

	/* Create a test file and try ACL on it. */
	fd = open("pretest", O_WRONLY | O_CREAT | O_EXCL, 0777);
	failure("Could not create test file?!");
	if (!assert(fd >= 0)) {
		acl_free(acl);
		return;
	}

#if HAVE_SUN_ACL
	n = facl_get(fd, 0, &acl2);
	if (n != 0) {
		close(fd);
		acl_free(acl);
	}
	if (errno == ENOSYS) {
		skipping("POSIX.1e ACLs are not supported on this filesystem");
		return;
	}
	failure("facl_get(): errno = %d (%s)", errno, strerror(errno));
	assertEqualInt(0, n);

	if (acl2->acl_type != ACLENT_T) {
		acl_free(acl2);
		skipping("POSIX.1e ACLs are not supported on this filesystem");
		return;
	}
	acl_free(acl2);

	func = "facl_set()";
	n = facl_set(fd, acl);
#else
	func = "acl_set_fd()";
	n = acl_set_fd(fd, acl);
#endif
	acl_free(acl);
	if (n != 0) {
#if HAVE_SUN_ACL
		if (errno == ENOSYS)
#else
		if (errno == EOPNOTSUPP || errno == EINVAL)
#endif
		{
			close(fd);
			skipping("POSIX.1e ACLs are not supported on this filesystem");
			return;
		}
	}
	failure("%s: errno = %d (%s)", func, errno, strerror(errno));
	assertEqualInt(0, n);

#if HAVE_SUN_ACL

#endif
	close(fd);

	/* Create a write-to-disk object. */
	assert(NULL != (a = archive_write_disk_new()));
	archive_write_disk_set_options(a,
	    ARCHIVE_EXTRACT_TIME | ARCHIVE_EXTRACT_PERM | ARCHIVE_EXTRACT_ACL);

	/* Populate an archive entry with some metadata, including ACL info */
	ae = archive_entry_new();
	assert(ae != NULL);
	archive_entry_set_pathname(ae, "test0");
	archive_entry_set_mtime(ae, 123456, 7890);
	archive_entry_set_size(ae, 0);
	assertEntrySetAcls(ae, acls2, sizeof(acls2)/sizeof(acls2[0]));
	assertEqualIntA(a, ARCHIVE_OK, archive_write_header(a, ae));
	archive_entry_free(ae);

	/* Close the archive. */
	assertEqualIntA(a, ARCHIVE_OK, archive_write_close(a));
	assertEqualInt(ARCHIVE_OK, archive_write_free(a));

	/* Verify the data on disk. */
	assertEqualInt(0, stat("test0", &st));
	assertEqualInt(st.st_mtime, 123456);
#if HAVE_SUN_ACL
	n = acl_get("test0", 0, &acl);
	failure("acl_get(): errno = %d (%s)", errno, strerror(errno));
	assertEqualInt(0, n);
#else
	acl = acl_get_file("test0", ACL_TYPE_ACCESS);
	failure("acl_get_file(): errno = %d (%s)", errno, strerror(errno));
	assert(acl != (acl_t)NULL);
#endif
	compare_acls(acl, acls2, sizeof(acls2)/sizeof(acls2[0]));
	acl_free(acl);
#endif	/* HAVE_SUN_ACL || HAVE_POSIX_ACL */
}

/*
 * Verify ACL read-from-disk.  This test is Platform-specific.
 */
DEFINE_TEST(test_acl_platform_posix1e_read)
{
#if !HAVE_SUN_ACL && !HAVE_POSIX_ACL
	skipping("POSIX.1e ACLs are not supported on this platform");
#else
	struct archive *a;
	struct archive_entry *ae;
	int n, fd, flags, dflags;
	char *func, *acl_text;
	const char *acl1_text, *acl2_text, *acl3_text;
#if HAVE_SUN_ACL
	acl_t *acl, *acl1, *acl2, *acl3;
#else
	acl_t acl1, acl2, acl3;
#endif

	/*
	 * Manually construct a directory and two files with
	 * different ACLs.  This also serves to verify that ACLs
	 * are supported on the local filesystem.
	 */

	/* Create a test file f1 with acl1 */
#if HAVE_SUN_ACL
	acl1_text = "user::rwx,"
	    "group::rwx,"
	    "other:rwx,"
	    "user:1:rw-,"
	    "group:15:r-x,"
	    "mask:rwx";
	n = acl_fromtext(acl1_text, &acl1);
	failure("acl_fromtext(): errno = %d (%s)", errno, strerror(errno));
	assertEqualInt(0, n);
#else
	acl1_text = "user::rwx\n"
	    "group::rwx\n"
	    "other::rwx\n"
	    "user:1:rw-\n"
	    "group:15:r-x\n"
	    "mask::rwx";
	acl1 = acl_from_text(acl1_text);
	failure("acl_from_text(): errno = %d (%s)", errno, strerror(errno));
	assert((void *)acl1 != NULL);
#endif
	fd = open("f1", O_WRONLY | O_CREAT | O_EXCL, 0777);
	failure("Could not create test file?!");
	if (!assert(fd >= 0)) {
		acl_free(acl1);
		return;
	}
#if HAVE_SUN_ACL
	/* Check if Solaris filesystem supports POSIX.1e ACLs */
	n = facl_get(fd, 0, &acl);
	if (n != 0)
		close(fd);
	if (n != 0 && errno == ENOSYS) {
		acl_free(acl1);
		skipping("POSIX.1e ACLs are not supported on this filesystem");
		return;
	}
	failure("facl_get(): errno = %d (%s)", errno, strerror(errno));
	assertEqualInt(0, n);

	if (acl->acl_type != ACLENT_T) {
		acl_free(acl);
		acl_free(acl1);
		close(fd);
		skipping("POSIX.1e ACLs are not supported on this filesystem");
		return;
	}

	func = "facl_set()";
	n = facl_set(fd, acl1);
#else
	func = "acl_set_fd()";
	n = acl_set_fd(fd, acl1);
#endif
	acl_free(acl1);

	if (n != 0) {
#if HAVE_SUN_ACL
		if (errno == ENOSYS)
#else
		if (errno == EOPNOTSUPP || errno == EINVAL)
#endif
		{
			close(fd);
			skipping("POSIX.1e ACLs are not supported on this filesystem");
			return;
		}
	}
	failure("%s: errno = %d (%s)", func, errno, strerror(errno));
	assertEqualInt(0, n);

	close(fd);

	assertMakeDir("d", 0700);

	/*
	 * Create file d/f1 with acl2
	 *
	 * This differs from acl1 in the u:1: and g:15: permissions.
	 *
	 * This file deliberately has the same name but a different ACL.
	 * Github Issue #777 explains how libarchive's directory traversal
	 * did not always correctly enter directories before attempting
	 * to read ACLs, resulting in reading the ACL from a like-named
	 * file in the wrong directory.
	 */
#if HAVE_SUN_ACL
	acl2_text = "user::rwx,"
	    "group::rwx,"
	    "other:---,"
	    "user:1:r--,"
	    "group:15:r--,"
	    "mask:rwx";
	n = acl_fromtext(acl2_text, &acl2);
	failure("acl_fromtext(): errno = %d (%s)", errno, strerror(errno));
	assertEqualInt(0, n);
#else
	acl2_text = "user::rwx\n"
	    "group::rwx\n"
	    "other::---\n"
	    "user:1:r--\n"
	    "group:15:r--\n"
	    "mask::rwx";
	acl2 = acl_from_text(acl2_text);
	failure("acl_from_text(): errno = %d (%s)", errno, strerror(errno));
	assert((void *)acl2 != NULL);
#endif
	fd = open("d/f1", O_WRONLY | O_CREAT | O_EXCL, 0777);
	failure("Could not create test file?!");
	if (!assert(fd >= 0)) {
		acl_free(acl2);
		return;
	}
#if HAVE_SUN_ACL
	func = "facl_set()";
	n = facl_set(fd, acl2);
#else
	func = "acl_set_fd()";
	n = acl_set_fd(fd, acl2);
#endif
	acl_free(acl2);
	if (n != 0)
		close(fd);
	failure("%s: errno = %d (%s)", func, errno, strerror(errno));
	assertEqualInt(0, n);
	close(fd);

	/* Create nested directory d2 with default ACLs */
	assertMakeDir("d/d2", 0755);

#if HAVE_SUN_ACL
	acl3_text = "user::rwx,"
	    "group::r-x,"
	    "other:r-x,"
	    "user:2:r--,"
	    "group:16:-w-,"
	    "mask:rwx,"
	    "default:user::rwx,"
	    "default:user:1:r--,"
	    "default:group::r-x,"
	    "default:group:15:r--,"
	    "default:mask:rwx,"
	    "default:other:r-x";
	n = acl_fromtext(acl3_text, &acl3);
	failure("acl_fromtext(): errno = %d (%s)", errno, strerror(errno));
	assertEqualInt(0, n);
#else
	acl3_text = "user::rwx\n"
	    "user:1:r--\n"
	    "group::r-x\n"
	    "group:15:r--\n"
	    "mask::rwx\n"
	    "other::r-x";
	acl3 = acl_from_text(acl3_text);
	failure("acl_from_text(): errno = %d (%s)", errno, strerror(errno));
	assert((void *)acl3 != NULL);
#endif

#if HAVE_SUN_ACL
	func = "acl_set()";
	n = acl_set("d/d2", acl3);
#else
	func = "acl_set_file()";
	n = acl_set_file("d/d2", ACL_TYPE_DEFAULT, acl3);
#endif
	acl_free(acl3);

	failure("%s: errno = %d (%s)", func, errno, strerror(errno));
	assertEqualInt(0, n);

	/* Create a read-from-disk object. */
	assert(NULL != (a = archive_read_disk_new()));
	assertEqualIntA(a, ARCHIVE_OK, archive_read_disk_open(a, "."));
	assert(NULL != (ae = archive_entry_new()));

#if HAVE_SUN_ACL
	flags = ARCHIVE_ENTRY_ACL_TYPE_POSIX1E
	    | ARCHIVE_ENTRY_ACL_STYLE_SEPARATOR_COMMA
	    | ARCHIVE_ENTRY_ACL_STYLE_SOLARIS;
	dflags = flags;
#else
	flags = ARCHIVE_ENTRY_ACL_TYPE_ACCESS;
	dflags = ARCHIVE_ENTRY_ACL_TYPE_DEFAULT;
#endif

	/* Walk the dir until we see both of the files */
	while (ARCHIVE_OK == archive_read_next_header2(a, ae)) {
		archive_read_disk_descend(a);
		if (strcmp(archive_entry_pathname(ae), "./f1") == 0) {
			acl_text = archive_entry_acl_to_text(ae, NULL, flags);
			assertEqualString(acl_text, acl1_text);
			free(acl_text);
		} else if (strcmp(archive_entry_pathname(ae), "./d/f1") == 0) {
			acl_text = archive_entry_acl_to_text(ae, NULL, flags);
			assertEqualString(acl_text, acl2_text);
			free(acl_text);
		} else if (strcmp(archive_entry_pathname(ae), "./d/d2") == 0) {
			acl_text = archive_entry_acl_to_text(ae, NULL, dflags);
			assertEqualString(acl_text, acl3_text);
			free(acl_text);
		}
	}

	archive_entry_free(ae);
	assertEqualInt(ARCHIVE_OK, archive_free(a));
#endif
}
Exemplo n.º 7
0
int
process_request (CTL_MSG * msg, struct sockaddr_in *sa_in, CTL_RESPONSE * rp)
{
  CTL_MSG *ptr;

  if (debug)
    {
      print_request ("process_request", msg);
    }

  if (acl_match (msg, sa_in))
    {
      syslog (LOG_NOTICE, "dropping request: %s@%s",
	      msg->l_name, inet_ntoa (sa_in->sin_addr));
      return 1;
    }

  rp->vers = TALK_VERSION;
  rp->type = msg->type;
  rp->id_num = htonl (0);
  if (msg->vers != TALK_VERSION)
    {
      syslog (LOG_ERR, "Bad protocol version %d", msg->vers);
      rp->answer = BADVERSION;
      return 0;
    }

  msg->id_num = ntohl (msg->id_num);
  msg->addr.sa_family = ntohs (msg->addr.sa_family);
  if (msg->addr.sa_family != AF_INET)
    {
      syslog (LOG_ERR, "Bad address, family %d", msg->addr.sa_family);
      rp->answer = BADADDR;
      return 0;
    }
  msg->ctl_addr.sa_family = ntohs (msg->ctl_addr.sa_family);
  if (msg->ctl_addr.sa_family != AF_INET)
    {
      syslog (LOG_WARNING, "Bad control address, family %d",
	      msg->ctl_addr.sa_family);
      rp->answer = BADCTLADDR;
      return 0;
    }
  /* FIXME: compare address and sa_in? */

  msg->pid = ntohl (msg->pid);

  switch (msg->type)
    {
    case ANNOUNCE:
      do_announce (msg, rp);
      break;

    case LEAVE_INVITE:
      ptr = find_request (msg);
      if (ptr)
	{
	  rp->id_num = htonl (ptr->id_num);
	  rp->answer = SUCCESS;
	}
      else
	insert_table (msg, rp);
      break;

    case LOOK_UP:
      ptr = find_match (msg);
      if (ptr)
	{
	  rp->id_num = htonl (ptr->id_num);
	  rp->addr = ptr->addr;
	  rp->addr.sa_family = htons (ptr->addr.sa_family);
	  rp->answer = SUCCESS;
	}
      else
	rp->answer = NOT_HERE;
      break;

    case DELETE:
      rp->answer = delete_invite (msg->id_num);
      break;

    default:
      rp->answer = UNKNOWN_REQUEST;
      break;
    }

  if (debug)
    print_response ("process_request response", rp);

  return 0;
}