mkdir -p equivalent in C that creates nested directories recursively - c

I want to create a new directory inside a new directory. Something like this:
#include <stdio.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <errno.h>
#include <string.h>
int main() {
const char * path = "/home/abc/testabc1/testabc2" ;
mode_t mode = 0777;
if (mkdir(path, mode) == -1) {
// printf("Error occurred : %s ", strerror(errno));
perror("abc");
}
else {
printf("Directory created\n");
}
}
When I do this I get this error:
abc: No such file or directory
If I remove testabc2 then I am able to create the directory with success. Why so ?

You can only create directories in existing directories. If you want to do the equivalent of mkdir -p you have to do the same thing it does, namely create one directory after another from the top of the path down.
In your case, that means mkdir of /home/abc/testabc1 before mkdir of /home/abc/testabc1/testabc2.
Your error message is also misleading since perror("abc"); will prepend any error with "abc:". It has nothing to do with the directory "abc".

Related

umask and chmod unexpected behaviour

I am trying to write simple program that changes file privileges using umask and chmod system-calls, but file privileges do not change as expected.
This is what I've tried:
Set umask to 0;
If the file doesn't exist, it is created by open system-call using O_CREAT flag, and then privileges are set to mode passed by command-line argument;
If the file already exists, change its privileges by chmod system-call.
#define _XOPEN_SOURCE 700
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <errno.h>
#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define check_error(expr, userMsg) \
do { \
if (!(expr)) { \
perror(userMsg); \
exit(EXIT_FAILURE); \
} \
} while(0)
int main(int argc, char** argv)
{
check_error(3 == argc, "use: ./umask path mode");
mode_t oldUmask = umask(0);
long mode = strtol(argv[2], NULL, 8);
int fd = open(argv[1], O_WRONLY|O_CREAT|O_EXCL, mode);
if (-1 == fd) {
if (EEXIST == errno) {
printf("[file already exists]\n");
check_error(-1 != chmod(argv[1], mode), "chmod failed");
} else {
perror("open failed");
exit(EXIT_FAILURE);
}
} else {
close(fd);
}
umask(oldUmask);
exit(EXIT_SUCCESS);
}
After compiling i tried:
./umask 1.txt 0744
Expected privileges would be -rwxr--r--, but after
ls -l
I get:
-rwxrwxrwx 1 root root 0 окт 19 14:06 1.txt
Again, after
./umask 1.txt 0744
this time I expected that chmod would internally change the privileges on existing file, but after listing I get the same:
[file already exists]
-rwxrwxrwx 1 root root 0 окт 19 14:06 1.txt
Both umask and chmod failed to set privileges as expected. What's wrong?
Files that I've created and tested the program on were created in a shared folder between Windows host machine and Linux virtual machine. I've started the program from Linux, trying to change the privileges of the file which I am not the owner of - it's Windows host machine, and that's why it doesn't let me change the privileges.

how to create folders using mkdir in c?

I'm trying to create a folder using mkdir in C but it wont't work
the code won't create the folders
#include <sys/stat.h>
#include <sys/types.h>
#include <stdio.h>
#include <string.h>
int main (){
char chemin[256];
char name[20];
//char fichier[100];
// FILE *fp;
strcpy(chemin,"/home/Deva/Documents/prog/C/la/sds");
mkdir(chemin,0755);
if (mkdir(chemin,0755)==-1){
printf("\nERROR\n");
} else { printf("fichier creer"); }
}
You have to create the intermediate directories first: e.g. you must create /home/Deva before creating /home/Deva/Documents, etc.
you are passing PATH not just directory name.
so please check below post would help
Recursive mkdir() system call on Unix
2 things:
1) You need to create the intermediate directories first.
2) You cannot create a directory twice, which you do here:
mkdir(chemin,0755);
if (mkdir(chemin,0755)==-1){

lstat returning <0

Basically, this should be a simple piece of code that opens a directory stream and looks for symbolic links. Whenever a symbolic link is found, it should print ("Symbolic link found");
However, the lstat(dirp->d_name,&bufcall always returns a value < 0, and I don't know why.
I created the two symbolic link opening the file folder, opening a terminal window inside the folder and running
ln -s ciao.txt link1 and
ln -s ciao2.txt link2
I know I should call closedir() later in my code, please don't care about this.
#include <fcntl.h>
#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <dirent.h>
#include <unistd.h>
void main (int argc, char* argv[])
{
char buffer[100],dir[100];
struct stat buf;
int x;
DIR *dp;
struct dirent *dirp;
if((dp=opendir(argv[1]))==NULL)
{
printf("\nError opening directory stream, now exiting...\n");
exit(-1);
}
while((dirp=readdir(dp))!=NULL)
{
lstat(dirp->d_name,&buf);
if(S_ISLNK(buf.st_mode))
printf("\n%s Is a symbolic link\n",dirp->d_name);
else
printf("\n%s Is not a symbolic link\n",dirp->d_name);
}
}
Some help would be appreciated. Thanks.
d_name is the file name in the directory, not a full path name. You must eather chdir into the directory you are looking at, or construct full path names for the files.
The simplest solution is to add this line just before your while loop:
chdir(argv[1]);

open() function with denied permission

I am trying to create a 'test.txt' file in root directory. Currently I am not a root user. my code is as follows:
#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
int main(){
int fd;
fd=open("/test.txt",O_CREAT|O_RDWR|O_TRUNC,0777);
perror("error: ");
close(fd);
return 0;
}
however, when I compile and execute it, I get the error:
error: : Permission denied
how can I make my code to have the permission to create a file in root directory?
P.S. I am trying to make this work so that I can use it later on to apply this method to my linux daemon program.
fd=open("/test.txt",O_CREAT|O_RDWR|O_TRUNC,0777);
In this line specify path correctly.(i.e) It is current working directory means, keep (dot) . before / like./test.txt

Create a directory

I am trying to create a directory using the following code. It compiles, but it does not create a directory. Any suggestions?
#include <stdio.h>
#include <string.h>
#include <sys/stat.h>
int main(void)
{
const char base[] = "filename";
char filename [ FILENAME_MAX ];
int number = 42;
sprintf(filename, "%s/%d", base, number);
printf("filename = \"%s\"\n", filename);
mkdir (filename, S_IRWXU);
return 0;
}
Does the "filename" directory already exist? mkdir() will only create one directory at a time; if the parent directory doesn't exist either, you'll have to create it separately, first.
Most probably it fails to create directory because you are trying to create a nested directory and its parent does not exist. mkdir cannot create directories recursively. But you can only guess unless you properly check return codes and errors in your program.

Resources