xref: /petsc/src/sys/fileio/fpath.c (revision 6a5217c03994f2d95bb2e6dbd8bed42381aeb015)
1 
2 #include <petscsys.h>
3 #if defined(PETSC_HAVE_PWD_H)
4 #include <pwd.h>
5 #endif
6 
7 /*@C
8    PetscGetFullPath - Given a filename, returns the fully qualified file name.
9 
10    Not Collective
11 
12    Input Parameters:
13 +  path     - pathname to qualify
14 .  fullpath - pointer to buffer to hold full pathname
15 -  flen     - size of fullpath
16 
17    Level: developer
18 
19 .seealso: PetscGetRelativePath()
20 @*/
21 PetscErrorCode  PetscGetFullPath(const char path[],char fullpath[],size_t flen)
22 {
23   size_t         ln;
24   PetscBool      flg;
25 
26   PetscFunctionBegin;
27   if (path[0] == '/') {
28     PetscCall(PetscStrncmp("/tmp_mnt/",path,9,&flg));
29     if (flg) PetscCall(PetscStrncpy(fullpath,path + 8,flen));
30     else     PetscCall(PetscStrncpy(fullpath,path,flen));
31     fullpath[flen-1] = 0;
32     PetscFunctionReturn(0);
33   }
34 
35   PetscCall(PetscStrncpy(fullpath,path,flen));
36   fullpath[flen-1] = 0;
37   /* Remove the various "special" forms (~username/ and ~/) */
38   if (fullpath[0] == '~') {
39     char tmppath[PETSC_MAX_PATH_LEN],*rest;
40     if (fullpath[1] == '/') {
41       PetscCall(PetscGetHomeDirectory(tmppath,PETSC_MAX_PATH_LEN));
42       rest = fullpath + 2;
43     } else {
44 #if defined(PETSC_HAVE_PWD_H)
45       struct passwd  *pwde;
46       char *p,*name;
47 
48       /* Find username */
49       name = fullpath + 1;
50       p    = name;
51       while (*p && *p != '/') p++;
52       *p   = 0;
53       rest = p + 1;
54       pwde = getpwnam(name);
55       if (!pwde) PetscFunctionReturn(0);
56 
57       PetscCall(PetscStrcpy(tmppath,pwde->pw_dir));
58 #else
59       PetscFunctionReturn(0);
60 #endif
61     }
62     PetscCall(PetscStrlen(tmppath,&ln));
63     if (tmppath[ln-1] != '/') PetscCall(PetscStrcat(tmppath+ln-1,"/"));
64     PetscCall(PetscStrcat(tmppath,rest));
65     PetscCall(PetscStrncpy(fullpath,tmppath,flen));
66     fullpath[flen-1] = 0;
67   } else {
68     PetscCall(PetscGetWorkingDirectory(fullpath,flen));
69     PetscCall(PetscStrlen(fullpath,&ln));
70     PetscCall(PetscStrncpy(fullpath+ln,"/",flen - ln));
71     fullpath[flen-1] = 0;
72     PetscCall(PetscStrlen(fullpath,&ln));
73     if (path[0] == '.' && path[1] == '/') {
74       PetscCall(PetscStrlcat(fullpath,path+2,flen));
75     } else {
76       PetscCall(PetscStrlcat(fullpath,path,flen));
77     }
78     fullpath[flen-1] = 0;
79   }
80 
81   /* Remove the automounter part of the path */
82   PetscCall(PetscStrncmp(fullpath,"/tmp_mnt/",9,&flg));
83   if (flg) {
84     char tmppath[PETSC_MAX_PATH_LEN];
85     PetscCall(PetscStrcpy(tmppath,fullpath + 8));
86     PetscCall(PetscStrcpy(fullpath,tmppath));
87   }
88   /* We could try to handle things like the removal of .. etc */
89   PetscFunctionReturn(0);
90 }
91