예제 #1
0
파일: main.c 프로젝트: ghent360/bluez
int main(int argc, char *argv[])
{
	int exit_status;

	if (getpid() == 1 && getppid() == 0)
		is_init = true;

	mainloop_init();

	printf("Bluetooth periperhal ver %s\n", VERSION);

	prepare_filesystem();

	if (is_init) {
		uint8_t addr[6];

		if (efivars_read("BluetoothStaticAddress", NULL,
							addr, 6) < 0) {
			printf("Generating new persistent static address\n");

			addr[0] = rand();
			addr[1] = rand();
			addr[2] = rand();
			addr[3] = 0x34;
			addr[4] = 0x12;
			addr[5] = 0xc0;

			efivars_write("BluetoothStaticAddress",
					EFIVARS_NON_VOLATILE |
					EFIVARS_BOOTSERVICE_ACCESS |
					EFIVARS_RUNTIME_ACCESS,
					addr, 6);
		}

		gap_set_static_address(addr);

		run_shell();
	}

	log_open();
	gap_start();

	if (is_init)
		attach_start();

	exit_status = mainloop_run_with_signal(signal_callback, NULL);

	if (is_init)
		attach_stop();

	gap_stop();
	log_close();

	return exit_status;
}
예제 #2
0
static bool prepare_block_device(void* ctx, const char* path)
{
	(void) ctx;
	struct harddisk* hd = harddisk_openat(AT_FDCWD, path, O_RDONLY);
	if ( !hd )
	{
		int true_errno = errno;
		struct stat st;
		if ( lstat(path, &st) == 0 && !S_ISBLK(st.st_mode) )
			return true;
		errno = true_errno;
		fatal("%s: %m", path);
	}
	if ( !harddisk_inspect_blockdevice(hd) )
	{
		if ( errno == ENOTBLK )
			return true;
		if ( errno == EINVAL )
			return warning("%s: %m", path), true;
		fatal("%s: %m", path);
	}
	if ( hds_used == hds_length )
	{
		// TODO: Potential overflow.
		size_t new_length = hds_length ? 2 * hds_length : 16;
		struct harddisk** new_hds = (struct harddisk**)
			reallocarray(hds, new_length, sizeof(struct harddisk*));
		if ( !new_hds )
			fatal("realloc: %m");
		hds = new_hds;
		hds_length = new_length;
	}
	hds[hds_used++] = hd;
	struct blockdevice* bdev = &hd->bdev;
	enum partition_error parterr = blockdevice_get_partition_table(&bdev->pt, bdev);
	if ( parterr == PARTITION_ERROR_ABSENT ||
	     parterr == PARTITION_ERROR_UNRECOGNIZED )
	{
		prepare_filesystem(path, bdev);
		return true;
	}
	else if ( parterr == PARTITION_ERROR_ERRNO )
	{
		if ( errno == EIO || errno == EINVAL )
			warning("%s: %s", path, partition_error_string(parterr));
		else
			fatal("%s: %s", path, partition_error_string(parterr));
		return true;
	}
	else if ( parterr != PARTITION_ERROR_NONE )
	{
		warning("%s: %s", path, partition_error_string(parterr));
		return true;
	}
	for ( size_t i = 0; i < bdev->pt->partitions_count; i++ )
	{
		struct partition* p = bdev->pt->partitions[i];
		assert(p->path);
		struct stat st;
		if ( stat(p->path, &st) == 0 )
		{
			// TODO: Check the existing partition has the right offset and
			//       length, but definitely do not recreate it if it already
			//       exists properly.
		}
		else if ( errno == ENOENT )
		{
			int mountfd = open(p->path, O_RDONLY | O_CREAT | O_EXCL);
			if ( mountfd < 0 )
				fatal("%s:˙%m", p->path);
			int partfd = mkpartition(hd->fd, p->start, p->length);
			if ( partfd < 0 )
				fatal("mkpartition: %s:˙%m", p->path);
			if ( fsm_fsbind(partfd, mountfd, 0) < 0 )
				fatal("fsbind: %s:˙%m", p->path);
			close(partfd);
			close(mountfd);
		}
		else
		{
			fatal("stat: %s: %m", p->path);
		}
		prepare_filesystem(p->path, &p->bdev);
	}
	return true;
}