Hello,

I've noticed that openvt looks more aggressively for a console device
and I would now like to try the same technique. Can you please try the
attached version?

Interestingly, gdm just tries /dev/console. Maybe it is not a big
problem in the systems where gdm runs.


Ciao,

Enrico

-- 
GPG key: 4096R/E7AD5568 2009-05-08 Enrico Zini <enr...@enricozini.org>
#include <stdio.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/wait.h>
#include <syslog.h>
#include <time.h>
#include <unistd.h>
#include <errno.h>
#include <fcntl.h>
#include <sys/vt.h>
#include <sys/ioctl.h>

#define Prog "getvt"
#define _(a) (a)

int try_vtstate(const char* dev, struct vt_stat* vtstat)
{
	int res = 0;
	int fd = open(dev, O_WRONLY | O_NOCTTY, 0);
	if (fd < 0)
		goto cleanup;
	if (ioctl (fd, VT_GETSTATE, vtstat) < 0)
		goto cleanup;
	res = 1;

cleanup:
	if (fd >= 0) close(fd);
	return res;
}

int get_vtstate(struct vt_stat* vtstat)
{
	if (try_vtstate("/dev/tty", vtstat)) return 1;
	if (try_vtstate("/dev/tty0", vtstat)) return 1;
	if (try_vtstate("/dev/console", vtstat)) return 1;
	return 0;
}

int main (int argc, char **argv)
{
	struct vt_stat vtstat;
	int vtnum = 1;
	char vtname[15];
	int res = 1;
	unsigned short vtmask;
	if (!get_vtstate(&vtstat))
	{
		fprintf (stderr, _("%s: cannot find or open the console\n"), Prog);
		goto cleanup;
	}
	printf("VT_GETSTATE succeeded\n");

	for (vtmask = 1 << vtnum; vtstat.v_state & vtmask; ++vtnum, vtmask <<= 1)
		printf("VT %d: busy\n", vtnum);
	if (!vtmask) {
		fprintf (stderr, _("%s: all VTs seem to be busy\n"), Prog);
		goto cleanup;
	}

	snprintf(vtname, 15, "/dev/tty%d", vtnum);
	printf("Got VT %s\n\n", vtname);

	res = open(vtname, O_RDWR | O_NOCTTY, 0);
	if (res < 0) {
		fprintf (stderr, _("%s: cannot open %s: %m\n"), Prog, vtname);
		goto cleanup;
	}
	printf("VT %s opened with fd %d\n", vtname, res);

	close(res);
	res = 0;

cleanup:
	return res;
}

Attachment: signature.asc
Description: Digital signature

Reply via email to