I'm trying to use find on Solaris 10 to list the contents of one directory, excluding subdirectories from the search. I tried a command based on the solution suggested by sdaau:

find /tmp -type d ! -perm -u+rx -prune -o -type f -name dsm\*

Unfortunately, in addition to returning the desired results, this still results in errors like these:

find: cannot read dir /tmp/hsperfdata_oracle4: Permission denied
find: cannot read dir /tmp/hsperfdata_jsweb: Permission denied

There are a couple of directories in /tmp to which the user executing find has neither read nor traverse (execute) authorization.

-bash-3.2$ ls -ld /tmp/hsp*
drwxr-x---   2 jsweb    other        117 Jan  5 13:00 /tmp/hsperfdata_jsweb
drwxr-x---   2 oracle4  dba4         117 Nov  5 19:51 /tmp/hsperfdata_oracle4
drwxr-xr-x   2 root     root         117 Jan 22 08:58 /tmp/hsperfdata_root

I need to find a way to eliminate these errors so that find does not end with a non-zero return code. What am I overlooking?


You can just discard those errors and ignore the exit status:

find /tmp -name dsm\* -type f 2> /dev/null || :

If you still want to keep find's stderr, to still be able to see errors other than failure to enter or list directories because of access permission restriction, you could try and use a syntax that detects those permission issues, but that's going to be tricky.

The directories you don't have access to depend on permission and ownership (user and group). You'd need something like:

export "PATH=$(getconf PATH):$PATH"
u=$(id -u) g=$(id -G | sed 's/ / -o -group /g'); IFS=" "
find /tmp -type d ! \( \
    -user "$u" -perm -u=rx -o \
    ! -user "$u" \( -group $g \) -perm -g=rx -o \
    ! -user "$u" ! \( -group $g \) -perm -o=rx \
  \) -prune -o -type f -name dsm\* -print

Having said that, in my tests, on Solaris 11, find will still complain about directories it can't read even if you've pruned them, and on Solaris 10, I can't even get it to do any action, let alone -prune on them.

So Solaris find seems to be beyond hope on that front. You could use perl's File::Find module instead.

Also note that the approach above only takes simple Unix permissions into consideration, not ACLs or other security restrictions.

  • I had to modify your idea a bit to get it to run. The version of id that support the -u and -G options is /usr/xpg4/bin/id on this system. Also, there were some semicolons and backslashes missing. With these modifications, it runs but still returns the same errors. – mlowry Jan 22 '16 at 15:02
  • See latest edit. getconf PATH will get you a PATH with the proper "id". But on Solaris 10, find is beyond hope. You can't prevent it from giving those errors by pruning the directories. – Stéphane Chazelas Jan 22 '16 at 15:26

In your examples, ! -perm -u+rx doesn't evaluate as true - owners still have those rights. You're supposed to use ! -perm -o+rx. So:

find /tmp -type d ! -perm -o+rx -prune -o -type f -name dsm\*
  • I am afraid that the same errors result from this command. I have tried a lot of variants of the -perm option. – mlowry Jan 22 '16 at 15:06
  • @mlowry That's all the I could spot, then, sorry. It works on Linux, and I tried to verify against Solaris man page - there's nothing that would indicate there should be some trouble (I don't have Solaris to check on). You could try a simple shell script for that. Maybe try parens, just to be sure? – TNW Jan 22 '16 at 16:00

Not sure what you're trying to accomplish, but since you don't want sub-directories, why not just run a ls and pipe it to grep? With maybe an awk or sort to meet your needs?

find /tmp -type d ! -perm -775 -prune -o -type f -name dsm\*
  • The -perm option does not appear to be working as expected. Just find /tmp -perm -775 fails to return the expected results. I'm beginning to understand why other threads I have read on this topic often include recommendations to use a different tool. – mlowry Jan 22 '16 at 15: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.