Reputation: 83
I want to create a file and the file has no write permission like this.
#include <stdio.h>
#include <fcntl.h>
#include <sys/stat.h>
main()
{
int fd;
fd=open("xxx",O_CREAT|O_WRONLY|O_APPEND,S_IRUSR);
if(fd==-1)
return 0;
else
if(write(fd,"created",7)==-1)
return 0;
if(close(fd)==-1)
return 0;
printf("OK");
}
I ran executable file and notice that the file xxx could be written to. Of cource, when I ran executable after first time, it worked like I expect when it could't be written to.
But how can I make the file xxx even can't be written to in first time (when it is created).
Upvotes: 2
Views: 2572
Reputation: 5297
You should remove:
O_WRONLY
And it should look like this:
#include <stdio.h>
#include <fcntl.h>
#include <unistd.h>
int main(void){
int fd;
fd=open("test.sh",O_CREAT|O_APPEND,S_IRUSR);
if(fd==-1)
return 0;
else
if(write(fd,"created",7)==-1)
return 0;
if(close(fd)==-1)
return 0;
printf("OK");
return 0;
}
And if you try to write that file, you will get:
[ Error writing test.sh: Permission denied ]
Anyway, on my Linux machine if I wanna check that file, I will do it like this:
#include <stdio.h>
#include <stdlib.h>
#include<unistd.h>
void fileCheck(const char *fileName){
if(!access(fileName, F_OK )){
printf("The File %s\t Found\n",fileName);
}else{
printf("The File %s\t not Found\n",fileName);
exit(1);
}
if(!access(fileName, R_OK )){
printf("The File %s\t can be read\n",fileName);
}else{
printf("The File %s\t cannot be read\n",fileName);
}
if(!access( fileName, W_OK )){
printf("The File %s\t it can be Edited\n",fileName);
}else{
printf("The File %s\t it cannot be Edited\n",fileName);
}
if(!access( fileName, X_OK )){
printf("The File %s\t is an Executable\n",fileName);
}else{
printf("The File %s\t is not an Executable\n",fileName);
}
}
int main (void){
char *fileName = "test.sh";
fileCheck(fileName);
return 0;
}
And the output says:
The File test.sh Found The File test.sh can be read The File test.sh it cannot be Edited The File test.sh is not an Executable
Upvotes: 3
Reputation: 5743
I can understand author's intent. He want to test the usage of S_IRUSR
. I will explain why it doesn't work at first time.
At first let us resolve your question. you can just remove O_WRONLY
and O_APPEND
flag, and add O_RDONLY
flag or not. Codes are following:
#include <stdio.h>
#include <fcntl.h>
#include <sys/stat.h>
int main() {
int fd;
fd = open("xxx", O_CREAT|O_RDONLY, S_IRUSR);
// or
// fd = open("xxx", O_CREAT, S_IRUSR);
if (fd == -1) {
printf("open failed\n");
return 0;
} else {
if (write(fd, "created", 7) == -1) {
printf("write failed\n");
return 0;
}
}
if (close(fd) == -1) {
printf("close failed\n");
return 0;
}
printf("OK\n");
}
then execute the program whenever, it will always says "write failed", and "xxx" is empty.
$ ls
test.c
$ make test
cc test.c -o test
$ ls
test test.c
$ ./test
write failed
$ ls
test test.c xxx
$ cat xxx
$ ./test
write failed
you said:
Of cource, when I ran executable after first time, it worked like I expect when it could't be written to.
in fact, if use your code, ran after first time, it is not couldn't be written to, it is not be open.
$ ls
test test.c
$ ./test
OK
$ ls
test test.c xxx
$ cat xxx
created
$ ./test
open failed
Then let us face the more important question, why S_ISUSR
doens't work at first time. let us run 'man 2 open', it says:
Note that this mode applies only to future accesses of the newly created file; the open() call that creates a read-only file may well return a read/write file descriptor.
It means S_ISUSR
only works after first time. Even S_ISUSR
is read only, but in fact still return read/write permission, the final permission depends on the flags, if the flag is O_WRONLY
, it can only write when create, if the flag is O_RDONLY
, it can only read when create.
let's do a test:
#include <stdio.h>
#include <fcntl.h>
#include <sys/stat.h>
int main() {
int fd;
char buf[10];
fd = open("xxx", O_CREAT|O_WRONLY, S_IRUSR);
if (fd == -1) {
printf("open failed\n");
return 0;
} else {
if (write(fd, "created", 7) == -1) {
printf("write failed\n");
return 0;
}
}
if (read(fd, buf, 7) == -1) {
printf("read failed\n");
return 0;
} else {
printf(buf);
}
if (close(fd) == -1) {
printf("close failed\n");
return 0;
}
printf("OK\n");
}
and result is expected, at first time, when file create, if has write permission and has no read permission, after first time, it open failed:
$ ls
test.c
$ make test
cc test.c -o test
$ ./test
read failed
$ ./test
open failed
$ cat xxx
created
And I can understand why they design the mode parameter only work after first time. You think, if S_IRUSR
works when file create, then the file is always empty and read only, it has no sense.
Upvotes: 1