Understanding File Permissions Linux

Linux File Permissions

Why Strict file Permissions and Ownership:

Linux OS is designed for a multi-user environment. An environment where more than one users are access the same file system and other resources at the same time. In such an environment file permissions and ownership would be a problem if you don’t configure it properly.

For example, one user have created a file and someone else deleted it mistakenly or deliberately, then first user would lose all the data he has compiled. This can be handled if you configure user rights properly.

Second example, one user executed a process and that process is gonna take a long time to be completed. Meanwhile somebody else stopped it, then the first user would not happy about this. For such things user permissions should be configured properly.

Understanding file Ownership in linux:

Each file/directory in linux is own by a specific user and a group. Therefore, permissions are separately defined for User, Group and Others.

User: User name of who owns the file/directory. By default the user who creates the file/directory is owner of that.

Group: The usergroup that owns the file. All the users in this group would have same file permissions.

Group permissions are usable if multiple users in a group are using some common file/directory. You need to make sure that the file is owned by the right group you want to give permissions to.

Others: A user who is not the owner of the file/directory and he also is not in the owner group.

Some people call it ‘world’ permissions.

Understanding File permissions in linux:

There are three types of file permissions in linux Read, Write and Execute. These permissions are separately defined for User, Group and Others.

Read: On a regular file, the read permission bit means the file can be opened and read. On a directory, the read permission means you can list the contents of the directory.

Write: On a regular file, this means you can modify the file means you can write new data to the file. In the case of a directory, the write permission means you can add, remove, and rename files in the directory.

This means that if a file has the write permission bit, you are allowed to modify the file’s contents, but you’re allowed to rename or delete the file only if the permissions of the file’s directory allow you to do so.

Execute: In the case of a regular file, this means you can execute the file as a program or a shell script. On a directory, the execute permission (also called the “search bit”) allows you to access files in the directory and enter it, with the “cd” command, for example.

However, note that although the execute bit lets you enter the directory, you’re not allowed to list its contents, unless you also have the read permissions to that directory.

Viewing file permissions in Linux:

You can list down directory contents with “ls” command but to see permissions of contents you need to get long listing of a directory contents with “ls -l” or “ll” command.

Following are the views with different listing types.

haris@harisaltaf-vaio:~/Downloads$ ls
DBs.zip images.jpg pc2-9.1.6.rar Scraper dl
haris@harisaltaf-vaio:~/Downloads$
haris@harisaltaf-vaio:~/Downloads$
haris@harisaltaf-vaio:~/Downloads$
haris@harisaltaf-vaio:~/Downloads$ ls -l
total 2276
-rw-r--r-- 1 haris haris 19527 2011-12-02 18:09 DBs.zip
-rw-r--r-- 1 haris haris 4712 2011-12-20 14:19 images.jpg
-rw-r--r-- 1 haris haris 2295246 2011-12-23 21:41 pc2-9.1.6.rar
drwxr-xr-x 2 haris haris 4096 2011-12-09 18:16 Scraper dl
haris@harisaltaf-vaio:~/Downloads$
haris@harisaltaf-vaio:~/Downloads$
haris@harisaltaf-vaio:~/Downloads$
haris@harisaltaf-vaio:~/Downloads$ ll
total 2284
drwxr-xr-x 3 haris haris 4096 2011-12-23 21:43 ./
drwxr-xr-x 55 haris haris 4096 2011-12-31 14:16 ../
-rw-r--r-- 1 haris haris 19527 2011-12-02 18:09 DBs.zip
-rw-r--r-- 1 haris haris 4712 2011-12-20 14:19 images.jpg
-rw-r--r-- 1 haris haris 2295246 2011-12-23 21:41 pc2-9.1.6.rar
drwxr-xr-x 2 haris haris 4096 2011-12-09 18:16 Scraper dl/
haris@harisaltaf-vaio:~/Downloads$

What does the long listing output means. The first column, having values like drwxr-xr-x, shows file permissions. Second column having an integer value shows number of links to the file. Third column shows file owner. Fourth column shows owner group. Fifth column shows size of file in bytes. Sixth column shows file’s last modification date and time. Seventh column shows file name.

Linux File Permissions
Linux File Permissions

The first column which shows file permissions is organised into four parts. Four parts are divided as d rwx r-x r-x. The First part shows File Type. Second part shows Owner permissions. Third part shows Group permissions. Fourth part shows Other permissions.

File Types:

d = directory
 = regular file
l = symbolic link
b = block device file
p = named pipe
c = character device file
s = Unix domain socket

Permission character Meaning:

r = read permission
w = write permission
x = execute permission
 = no permission

To see hot to Set File Permissions in Linux see my next post.

Get Return Code of a Program within a Java Program

In previous post i wrote about shell scripts arguments having spaces. Now, in this post i am writing about how to get return code of a program within a java program.

Problem statement:

Get return code of a program while you execute that program from the java code. This program may be either a shell command/script or another java program.

Get Java Return Code POC:

The following java code snippets are written for this POC.

Program 1:

I have a simple java application which return the same integer as its return code which i pass it as an argument. Following i have shared that.

package com.harisaltaf;

public class ReturnCode {
public static void main(String[] args) {
System.out.println("Returning code=" + args[0]);
System.exit(Integer.parseInt(args[0]));
}
}

Program 2:

I have written another java application which executes this application and get its return code. Following is that piece of code.

package com.harisaltaf;

public class GetReturnCode {
public static void main(String[] args) {
// String[] command = { "./linux_shell_script.sh" };
String[] command = {
"sh",
"-c",
"cd /home/haris/workspace/get_java_return_code"
+ "&& java -cp java_return_code.jar com.harisaltaf.ReturnCode 5" };
ShellExecutor executor = new ShellExecutor();
try {
executor.execute(command);

System.out.println("Command Return Code= "
+ executor.getReturnCode());
System.out.println("Command Result= " + executor.getScriptResult());
System.out.println("Command Error= " + executor.getScriptError());

} catch (Exception e) {
System.out.println(e.getMessage());
}
}

You can see i have written two commands. In first command i am executing the program 1 from a shell script while in second command i am running that directly as a shell command.

Below is the shell script code. Don’t forget to change shell script file writes.

echo ""
echo "---------------------------------------------"

echo "---result of ls:"
cd /home/haris/workspace
ls

echo "---result of java program:"
cd /home/haris/workspace/get_java_return_code
java -cp java_return_code.jar com.harisaltaf.ReturnCode 5

echo "---result of ls again:"
ls
echo "---------------------------------------------"

Output:

Executing Shell Script:

When i run the program with the help of shell script, i get the following output.

Command Return Code= 0
Command Result=
---------------------------------------------
---result of ls:
get_java_return_code
java_return_code
---result of java program:
Returning code=5
---result of ls again:
bin
java_return_code.jar
linux_shell_script.sh
src
---------------------------------------------

Command Error= null

You see in the Java code you didn’t get the correct return code of program 1 in you 2nd java application. The actual code of the program 1 should be equal to 5 as we gave it as input but the returned code of the shell script is 0 as in output “Command Return Code= 0”. This is because when you run some commands from shell script then the return code returned is the return code of the complete shell script not of only the program you specified.

When executing as direct Shell Command:

When i run the program with java command executing directly from java application, i get the following output.

Command Return Code= 5
Command Result= Returning code=5

Command Error= null

You see i get the correct return code now.

Source code:

Download source code from here: get_java_return_code

Shell Script Arguments with Spaces from JAVA

Today i was doing my office work. It was about automating a process by calling shell scripts from java code. I got a very time consuming issue it took my almost 4 hours to resolve it. Actually in start i searched for replacement not for the direct solution.

Problem Statement:

The problem was that whenever you pass some shell script arguments with spaces from java code which have spaces in it the value isn’t passed correctly. It breaks the value at first space. For example:

If you have passed “second argument” form java code then in shell script the statement “export SECOND_PARAM=$2” will set the value of SECOND_PARAM to “second” only.

Shell Script Arguments with Spaces POC:

The following java code snippet is written for this POC.

public static void main(String[] args) {
String userDir = System.getProperty("user.dir");
System.out.println("User dir : " + System.getProperty("user.dir"));
Integer intVal = -1;
String[] command = { "./resources/dumpScript.sh", "firstArgument", "second Argument" };

try {

BufferedReader stdInput = null;
BufferedReader stdError = null;

Process p = Runtime.getRuntime().exec(command);
stdInput = new BufferedReader(new InputStreamReader(p
.getInputStream()));
stdError = new BufferedReader(new InputStreamReader(p
.getErrorStream()));

String line;
System.out.println("===============stdInput================");
line = stdInput.readLine();
while (line != null) {
System.out.println(line);
line = stdInput.readLine();
}
System.out.println("=======================================");

System.out.println("===============stdError================");
line = stdError.readLine();
while (line != null) {
System.out.println(line);
line = stdError.readLine();
}
System.out.println("=======================================");

intVal = p.waitFor();

try {
if (stdInput != null)
stdInput.close();
} catch (Exception ignored) {
}
try {
if (stdError != null)
stdError.close();
} catch (Exception ignored) {
}

} catch (Exception e) {
System.out.println(e.getMessage());
}
System.setProperty("user.dir", userDir);
System.out.println("Current dir : " + System.getProperty("user.dir"));
}

and the following is the shell script written for this POC.

echo "start of the Shell script."

export FIRST_PARAM=$1
export SECOND_PARAM=$2

echo "First arg= " $FIRST_PARAM
echo "Second arg= " $SECOND_PARAM

echo "end of the Shell script."

When i run the code first i got the following output:


User dir : /home/haris/workspace/Shell Script Arguments with Spaces POC
java.io.IOException: Permission denied
Current dir : /home/haris/workspace/Shell Script Arguments with Spaces POC

This was because my shell script file did not have execute permissions on linux. To give permissions to your shell scripts do the following:

Set File permissions in Linux:

cd "path of directory where your shell script is"
chmod 777 dumpScript.sh

After successful execution of my shell script i got the following output:

User dir : /home/haris/workspace/Shell Script Arguments with Spaces POC
===============stdInput================
start of the Shell script.
First arg= firstArgument
Second arg= second
end of the Shell script.
=======================================
===============stdError================
=======================================
Current dir : /home/haris/workspace/Shell Script Arguments with Spaces POC

Here you can see “Second arg= second” You can see in java code snippet that i passed  “second Argument” as argument to this variable but only “second” could be set in the variable.

Solution for shell scripts arguments with spaces:

Change your shell script. Simply add double quotes around “$2”. The new shell script is copied below:

echo "start of the Shell script."

export FIRST_PARAM=$1
export SECOND_PARAM="$2"

echo "First arg= " $FIRST_PARAM
echo "Second arg= " $SECOND_PARAM

echo "end of the Shell script."

After running the program again you can see the correct output. Following snippet shows the correct output i got after this modification.

User dir : /home/haris/workspace/Shell Script Arguments with Spaces POC
===============stdInput================
start of the Shell script.
First arg=  firstArgument
Second arg=  second Argument
end of the Shell script.
=======================================
===============stdError================
=======================================
Current dir : /home/haris/workspace/Shell Script Arguments with Spaces POC

Source Code:

Download code from here: Shell Script Arguments with Spaces POC

References:

http://stackoverflow.com/questions/905891/passing-argument-containing-space-in-shell-script