1

I'm facing a really strange problem using udev. As I already explained here I'm trying to access some folders/files as a no root user Here are my udev rules for the gpio folder:

KERNEL=="gpio*", SUBSYSTEM=="gpio", ACTION=="add", PROGRAM="/bin/sh -c 'chown -R dave:users /sys/class/gpio; chmod -R 777 /sys/class/gpio'"
KERNEL=="gpio*", SUBSYSTEM=="gpio", ACTION=="add", PROGRAM="/bin/sh -c 'chown -R dave:users /sys/class/virtual/gpio; chmod -R 777 /sys/class/virtual/gpio'"
KERNEL=="gpio*", SUBSYSTEM=="gpio", ACTION=="add", PROGRAM="/bin/sh -c 'chown -R dave:users /sys%p; chmod -R 770 /sys%p'"

which apply in the right way as expected to do. Infact after a reboot I get the rights I defined in the rules:

dave@arm:~$ ls -l /sys/class/gpio/
total 0
-rwxrwxrwx 1 dave users 4096 Jan  9 20:56 export
lrwxrwxrwx 1 dave users    0 Jan  9 20:56 gpiochip0 -> ../../devices/platform/ocp/44e07000.gpio/gpio/gpiochip0
lrwxrwxrwx 1 dave users    0 Jan  9 20:56 gpiochip32 -> ../../devices/platform/ocp/4804c000.gpio/gpio/gpiochip32
lrwxrwxrwx 1 dave users    0 Jan  9 20:56 gpiochip64 -> ../../devices/platform/ocp/481ac000.gpio/gpio/gpiochip64
lrwxrwxrwx 1 dave users    0 Jan  9 20:56 gpiochip96 -> ../../devices/platform/ocp/481ae000.gpio/gpio/gpiochip96
-rwxrwxrwx 1 dave users 4096 Jan  9 20:56 unexport

Now: it happens something really strange. I wrote I simple C++ program which does use the boost libraries to access and to write into files. Here I post a scracth of my program which consists of classes just as an example:

/*
 * @brief drives the gpio-pin high or low
 * @param the pin number, the state (high or low)
 * @return the success of the operation
 * 
 */
int GPIOclass::digitalWrite( unsigned int pin_label, unsigned int state ) 
{
    /* Check whether the Pin state has been correctly set or not */
    if( ( state != HIGH ) && ( state != LOW ) ) {
        std::cerr << "WARNING: Check again the value you want to write. It must be HIGH or LOW!" << std::endl;
        return EXIT_FAILURE;
    }

    /* Write the desired Pin value */
    boost::filesystem::fstream fs;

    boost::filesystem::path path_pin = "/sys/class/gpio";
    path_pin /= "/gpio" + std::to_string( pin_label );
    path_pin /= "/value";

    fs.open( path_pin, std::fstream::out );
    if( fs.is_open() ) {
        fs << state;
        fs.close();
    } else {
        std::cerr << "ERROR: I couldn't open " << path_pin << " file" << std::endl;
        return EXIT_FAILURE;
    }

    return EXIT_SUCCESS;
}

The strange thing is that I cannot access the required pin, because in the exported folder I found only one link and not the usual files and folders to drive the gpio. What I find is the only entry:

dave@arm:~$ ls -l /sys/class/gpio/gpio60
lrwxrwxrwx 1 dave users 0 Jan  9 20:58 /sys/class/gpio/gpio60 -> ../../devices/platform/ocp/4804c000.gpio/gpio/gpio60

But going into the directory I can see more files and folders than above:

dave@arm:/sys/class/gpio/gpio60$ ls -l
total 0
-rwxrwx--- 1 dave users 4096 Jan  9 21:11 active_low
lrwxrwxrwx 1 dave users    0 Jan  9 21:11 device -> ../../../4804c000.gpio
-rwxrwx--- 1 dave users 4096 Jan  9 21:11 direction
-rwxrwx--- 1 dave users 4096 Jan  9 21:11 edge
drwxrwx--- 2 dave users    0 Jan  9 21:11 power
lrwxrwxrwx 1 dave users    0 Jan  9 21:11 subsystem -> ../../../../../../class/gpio
-rwxrwx--- 1 dave users 4096 Jan  9 21:11 uevent
-rwxrwx--- 1 dave users 4096 Jan  9 21:11 value

so it seems that there are some visibility rules or something like that. Why I get 2 different results if I look into the folder from outside or if I look from inside the folder?

Starting the same program using sudo works perfectly.


UPDATE: I did exactly what suggested in the answer below. The answer is right but I can't use the exported gpio as a normal user. So I m looking for a new rule which let me to change the group and the owner of the linked folder:

/sys/devices/platform/ocp/4804c000.gpio 

as suggested in the answer.

The problem is now that I m trying to write a new rule which does exactly that. Once I retrieved the following informations:

@arm:~/workspace/auto/build$ udevadm info --path=/sys/devices/platform/ocp/4804c000.gpio --attribute-walk

Udevadm i...

  looking at device '/devices/platform/ocp/4804c000.gpio':
    KERNEL=="4804c000.gpio"
    SUBSYSTEM=="platform"
    DRIVER=="omap_gpio"
    ATTR{driver_override}=="(null)"

  looking at parent device '/devices/platform/ocp':
    KERNELS=="ocp"
    SUBSYSTEMS=="platform"
    DRIVERS==""
    ATTRS{driver_override}=="(null)"

  looking at parent device '/devices/platform':
    KERNELS=="platform"
    SUBSYSTEMS==""
    DRIVERS==""

I added the following rules to my existing udev-rule:

KERNEL=="gpio*", SUBSYSTEM=="gpio", ACTION=="add", PROGRAM="/bin/sh -c 'chown -R bbb:gpio /sys/class/gpio; chmod -R 777 /sys/class/gpio'"
KERNEL=="gpio*", SUBSYSTEM=="gpio", ACTION=="add", PROGRAM="/bin/sh -c 'chown -R bbb:gpio /sys/class/virtual/gpio; chmod -R 777 /sys/class/virtual/gpio'"
KERNEL=="gpio*", SUBSYSTEM=="gpio", ACTION=="add", PROGRAM="/bin/sh -c 'chown -R bbb:gpio /sys%p; chmod -R 776 /sys%p'"
KERNEL=="4804c000.gpio", SUBSYSTEM=="platform", ACTION=="add", PROGRAM="/bin/sh -c 'chown -R bbb:gpio /sys/devices/platform/ocp/4804c000.gpio; chmod -R 777 /sys/devices/platform/ocp/4804c000.gpio'"
KERNEL=="481ae000.gpio", SUBSYSTEM=="platform", ACTION=="add", PROGRAM="/bin/sh -c 'chown -R bbb:gpio /sys/devices/platform/ocp/481ae000.gpio; chmod -R 777 /sys/devices/platform/ocp/481ae000.gpio'"
KERNEL=="481ac000.gpio", SUBSYSTEM=="platform", ACTION=="add", PROGRAM="/bin/sh -c 'chown -R bbb:gpio /sys/devices/platform/ocp/481ac000.gpio; chmod -R 777 /sys/devices/platform/ocp/481ac000.gpio'"
KERNEL=="44e07000.gpio", SUBSYSTEM=="platform", ACTION=="add", PROGRAM="/bin/sh -c 'chown -R bbb:gpio /sys/devices/platform/ocp/44e07000.gpio; chmod -R 777 /sys/devices/platform/ocp/44e07000.gpio'"

Running as a normal user I still get the following error:

ERROR: I couldn't open "/sys/class/gpio/gpio67/value" file
ERROR: I couldn't open "/sys/class/gpio/gpio69/value" file
ERROR: I couldn't open "/sys/class/gpio/gpio66/value" file
ERROR: I couldn't open "/sys/class/gpio/gpio69/value" file

from my C++ program above.

I really can't understand since the rights are correctly set:

bbb@arm:~/workspace/build$ ls -l /sys/class/gpio/gpio60/
total 0
-rwxrwxrw- 1 bbb gpio 4096 Jan 11 17:50 active_low
lrwxrwxrwx 1 bbb gpio    0 Jan 11 17:50 device -> ../../../4804c000.gpio
-rwxrwxrw- 1 bbb gpio 4096 Jan 11 17:50 direction
-rwxrwxrw- 1 bbb gpio 4096 Jan 11 17:50 edge
drwxrwxrw- 2 bbb gpio    0 Jan 11 17:50 power
lrwxrwxrwx 1 bbb gpio    0 Jan 11 17:50 subsystem -> ../../../../../../class/gpio
-rwxrwxrw- 1 bbb gpio 4096 Jan 11 17:50 uevent
-rwxrwxrw- 1 bb gpio 4096 Jan 11 17:50 value

and the problem with the link seems to be fixed now:

bbb@arm:~/workspace/build$ ls -l /sys/class/gpio
total 0
-rwxrwxrwx 1 bbb gpio 4096 Jan 11 17:50 export
lrwxrwxrwx 1 bbb gpio    0 Jan 11 17:50 gpio48 -> ../../devices/platform/ocp/4804c000.gpio/gpio/gpio48
lrwxrwxrwx 1 bbb gpio    0 Jan 11 17:50 gpio60 -> ../../devices/platform/ocp/4804c000.gpio/gpio/gpio60
lrwxrwxrwx 1 bbb gpio    0 Jan 11 17:50 gpio66 -> ../../devices/platform/ocp/481ac000.gpio/gpio/gpio66
lrwxrwxrwx 1 bbb gpio    0 Jan 11 17:50 gpio67 -> ../../devices/platform/ocp/481ac000.gpio/gpio/gpio67
lrwxrwxrwx 1 bbb gpio    0 Jan 11 17:50 gpio68 -> ../../devices/platform/ocp/481ac000.gpio/gpio/gpio68
lrwxrwxrwx 1 bbb gpio    0 Jan 11 17:50 gpio69 -> ../../devices/platform/ocp/481ac000.gpio/gpio/gpio69
lrwxrwxrwx 1 bbb gpio    0 Jan 11 17:49 gpiochip0 -> ../../devices/platform/ocp/44e07000.gpio/gpio/gpiochip0
lrwxrwxrwx 1 bbb gpio    0 Jan 11 17:49 gpiochip32 -> ../../devices/platform/ocp/4804c000.gpio/gpio/gpiochip32
lrwxrwxrwx 1 bbb gpio    0 Jan 11 17:49 gpiochip64 -> ../../devices/platform/ocp/481ac000.gpio/gpio/gpiochip64
lrwxrwxrwx 1 bbb gpio    0 Jan 11 17:49 gpiochip96 -> ../../devices/platform/ocp/481ae000.gpio/gpio/gpiochip96
-rwxrwxrwx 1 bbb gpio 4096 Jan 11 17:49 unexport

what I m doing wrong?


UPDATE: I'm really having hard time to try to understand what is going in this distribution. I came up whit this minimal example (under this link you can find the cmakelists to compile it) to open and write into the exported folders for each pin. I'm now using a beaglebone (with ubuntu). The uder rules are defined above. I didn't change them.

Trying to run the program with my user "bbb" I get the following errors:

bbb@arm:~/workspace/auto/test/build$ ./myprog 
ERROR: the direction of pin "/sys/class/gpio/gpio67/direction" cannot be set.
Reason: Permission denied
ERROR: the value of the "/sys/class/gpio/gpio67/value" cannot be defined.
Reason: Permission denied
...

I added the user "bbb" to all the groups which belongs to the default user "ubuntu".

What can I do?

  • What is the errno value after trying to open the file? What makes you think that it's a permission problem? Post a small, compilable program that reproduces the problem and that prints out the full error information. – Gilles Jan 11 '16 at 17:03
  • Because running the same program with 'sudo' I can drive my GPIO pins exactly as expected. Tomorrow I m going to tell you what is the errno. I don't have the board right now. – Dave Jan 11 '16 at 18:52
  • The output of cerror is posted above. – Dave Jan 16 '16 at 14:53
2

/sys/class/gpio/gpio60 is a symbolic link. That's a special type of file that points to another file. When accessing the file contents, symbolic links are transparent: they act like their target (the file they point to). But when listing directories, symbolic links appear as themselves; ls -l shows them with l in the leftmost column, and shows their target after -> on the right. When accessing metadata, it depends.

chmod -R … /sys/class/gpio affects the directory tree starting at /sys/class/gpio. This includes entries such as /sys/class/gpio/gpio60. But /sys/class/gpio/gpio60 is a symbolic link, pointing somewhere else in the directory tree; the chmod command does not affect the target of the symbolic link.

When you try to access files under /sys/class/gpio/gpio60, or when you run cd /sys/class/gpio/gpio60, this accesses the directory that the symbolic link points to (access to the content of the directory). This works as root but not as non-root because that directory is accessible to root only.

To make that directory accessible to other users, you would need to run chmod … /sys/devices/platform/ocp/4804c000.gpio/gpio/gpio60.

However, rather than change the ownership, it would be simpler to add your user to the gpio group:

adduser dave gpio
  • That's a very detailed explanation of the problem but it still doesn't fix my problem – Dave Jan 11 '16 at 16:26

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.