[Solved]How to reboot/poweroff as normal User

For discussions about programming and projects not necessarily associated with Porteus.
Post Reply
User avatar
sabir
White ninja
White ninja
Posts: 12
Joined: 14 May 2014, 19:54
Distribution: Porteus LXDE 32
Location: Russia

[Solved]How to reboot/poweroff as normal User

Post#1 by sabir » 14 May 2014, 20:40

Hi all!
How to restart Linux from inside a C program without qt/gtk/sudo/python/java script/bash script/pressing poweroff button manually/etc?
I mean using only real system/kernel calls and pure C libs, for example:

#include <unistd.h>
#include <sys/reboot.h>
#define LINUX_REBOOT_CMD_POWER_OFF 0x4321fedc
sync();
reboot(RB_POWER_OFF); / reboot(LINUX_REBOOT_CMD_POWER_OFF);

or

#include <stdio.h>
int main()
{
setuid (0);
system("shutdown -P now");
return 0;
}

It works under root user only, but it is wrong way (security). User is in power group (/etc/group/power:x:84:guest).
Please don't tell me about:
just press lxde panel->menu->Logout
cairo-dock->Logout->Shutdown/Restart
su->root password->reboot/poweroff
execl("/usr/bin/sudo", "/sbin/shutdown", "-h", "1:30", (char*)NULL);

Thanks :)
Last edited by sabir on 20 May 2014, 03:48, edited 1 time in total.

tome
Contributor
Contributor
Posts: 561
Joined: 26 Jun 2013, 14:03
Distribution: x64 Openbox
Location: Poland
Contact:

Re: How to reboot/poweroff as normal User

Post#2 by tome » 15 May 2014, 04:02


User avatar
sabir
White ninja
White ninja
Posts: 12
Joined: 14 May 2014, 19:54
Distribution: Porteus LXDE 32
Location: Russia

Re: How to reboot/poweroff as normal User

Post#3 by sabir » 15 May 2014, 17:53

Thanks, man :)
As I understood there is no way to do it as normal user, unless run any prog with root privileges.

tome
Contributor
Contributor
Posts: 561
Joined: 26 Jun 2013, 14:03
Distribution: x64 Openbox
Location: Poland
Contact:

Re: How to reboot/poweroff as normal User

Post#4 by tome » 15 May 2014, 18:49

root privileges are unneeded

User avatar
sabir
White ninja
White ninja
Posts: 12
Joined: 14 May 2014, 19:54
Distribution: Porteus LXDE 32
Location: Russia

Re: How to reboot/poweroff as normal User

Post#5 by sabir » 17 May 2014, 05:42

tome wrote:root privileges are unneeded
To run "/usr/bin/dbus-send" the root privileges are unneeded, but "dbus" itself has root privileges (/usr/bin/dbus-send owner:root, group:root). A normal user just asks dbus-send to send his message to the ConsoleKit/UPower. The /usr/bin/upower and the /usr/bin/ck-* have root privileges too. Am I wrong?

tome
Contributor
Contributor
Posts: 561
Joined: 26 Jun 2013, 14:03
Distribution: x64 Openbox
Location: Poland
Contact:

Re: How to reboot/poweroff as normal User

Post#6 by tome » 17 May 2014, 10:14

I don't know but you don't need root password.

User avatar
brokenman
Site Admin
Site Admin
Posts: 5439
Joined: 27 Dec 2010, 03:50
Distribution: Porteus v3.2rcX all desktops
Location: Brazil
Contact:

Re: How to reboot/poweroff as normal User

Post#7 by brokenman » 18 May 2014, 01:26

No you are not wrong. This is the process when guest hits the shutdown button. You should be able to accomplish this from within a script like so:

Code: Select all

/usr/bin/dbus-send --system --print-reply \
--dest="org.freedesktop.ConsoleKit" \
/org/freedesktop/ConsoleKit/Manager \
org.freedesktop.ConsoleKit.Manager.Stop
This is what tome says in his thread.
How do i become super user?
Wear your underpants on the outside and put on a cape.

User avatar
sabir
White ninja
White ninja
Posts: 12
Joined: 14 May 2014, 19:54
Distribution: Porteus LXDE 32
Location: Russia

Re: How to reboot/poweroff as normal User

Post#8 by sabir » 19 May 2014, 07:33

brokenman wrote:This is what tome says in his thread.
Yeah, I understood. But I'd like to reboot my own computer directly as a normal user, without any root privileged progs. I mean, I'd like to call reboot(RB_POWER_OFF) directly as a non-privileged user :)

User avatar
fanthom
Site Admin
Site Admin
Posts: 4548
Joined: 28 Dec 2010, 02:42
Distribution: Porteus Kiosk
Location: Poland, currently - Cork, IE
Contact:

Re: How to reboot/poweroff as normal User

Post#9 by fanthom » 19 May 2014, 19:28

linux is designed to prevent this

Code: Select all

guest@porteus:~$ /sbin/reboot
reboot: must be superuser.
Please add [Solved] to your thread title if the solution was found.

User avatar
brokenman
Site Admin
Site Admin
Posts: 5439
Joined: 27 Dec 2010, 03:50
Distribution: Porteus v3.2rcX all desktops
Location: Brazil
Contact:

Re: [Solved]How to reboot/poweroff as normal User

Post#10 by brokenman » 21 May 2014, 01:50

OK i understood you were writing a script that would run on other systems too. If this is just for your box then perhaps change ownership/access rights of the binaries and put them in /usr/bin. Havn't tried it since the shutdown button works as guest fo rme. If you're in terminal then just su to root and shutdown.

Another option is to create a script as suggested above, put it in /usr/bin and call it as guest. I tested this and it works fine.
How do i become super user?
Wear your underpants on the outside and put on a cape.

User avatar
sabir
White ninja
White ninja
Posts: 12
Joined: 14 May 2014, 19:54
Distribution: Porteus LXDE 32
Location: Russia

Re: [Solved]How to reboot/poweroff as normal User

Post#11 by sabir » 30 May 2014, 03:41

brokenman wrote:If this is just for your box then perhaps change ownership/access rights of the binaries and put them in /usr/bin.
Make our reboot binary file:

Code: Select all

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>

#include <linux/reboot.h>
#include <sys/reboot.h>

#include <grp.h>
#include <pwd.h>

#include <error.h>
#include <errno.h>

static gid_t * read_groups(void)
{
	int n;
	gid_t *groups;
	
	n = getgroups(0, NULL);

	if(n < 0)
	{
		fprintf(stderr, "Unable to retrieve groups: %m\n");
		return NULL;
	}

	groups = malloc(n * sizeof(gid_t));
	if(!groups) return NULL;

	if(getgroups(n, groups) < 0)
	{
		fprintf(stderr, "Unable to retrieve groups: %m\n");
		free(groups);
		return NULL;
	}
	return groups;
}

static int reboot_allowed()
{
	struct group *gr;
	gid_t *groups;
	int i;
	
	gr = getgrnam("power");
	if(gr)
	{
		groups = read_groups();
		if (groups)
		{
			for (i = 0; groups[i]; ++i)
			{
				if (groups[i] == gr->gr_gid)
				{
					free(groups);
					return 1;
				}
			}
			free(groups);
		}
	}
	return 0;
}

int main()
{
	struct passwd *pw;
	
	pw = getpwuid(getuid());
	if(pw == NULL) error(1, errno, "failed to get username\n");
	
	if(!reboot_allowed()) error(1, 0, "Permission denied\n");
	
	sync();
	reboot(LINUX_REBOOT_CMD_RESTART);
	return 0;
}
Then change ownership/access rights of the binary and put it in /usr/bin:
Run it as root of course :)

Code: Select all

cp re-boot /usr/bin/
chown root /usr/bin/re-boot
chmod +s /usr/bin/re-boot
And now you can reboot you're computer as normal user. Just run re-boot (where re-boot is the binary name), but be carefull it's unsecure way to do it :)

Post Reply